media updates for v3.19-rc1

-----BEGIN PGP SIGNATURE-----
 Version: GnuPG v1
 
 iQIcBAABAgAGBQJUhxhbAAoJEAhfPr2O5OEV4JwP/2I7D2KGz5tdNGDAh1H8+swR
 hoj3tX7HLhwBmF6XIUlMYbk5L/ClDace6kcjT6OjwJ9SktrrKks6ZSsYsBjCIyOC
 yS7xNQArUKzWk4vV+uJVAvtF8V57LLFul8dhHk0JJwAxrkWnPvDdfJNs4PhUAkgn
 1i0PPshNo5Ow/+4YMiOjEDR+q9TMSUUzaq5zkPF7AFCnykuJ1wUJwUE0qjTfGi+4
 gl1yMye0TEawTYSM8h/+Lh7wosNFZYcXg85r04A6a8h6GLgg0h6KSOJjyPITmQ+j
 hLdtyiYs8a6XT+Y8o416zxpbSozo7KXCUTtet/N5g+lgQMqZqSd9WxE52SOY+kfd
 UVeob0VfWR0xdDzaJp5rLQ/MQ16RTHaHppgUidFxxGe9D5f9JM/88I0OfwNzl4uO
 cv2cyeNktHH6bcjfOGqxSVmZWgAm6q6qU7MN07PoN+5TcUlYTAOi1WLE5K+7HGgw
 CxzOZ61oxi/OO1FapaVoipq6ycjltTql2kbcARvmrRrbge0ocAqHxHqFyUbDDhNw
 Wn/O6VzLfpW0vGTacC6+xcUSpIhwajJ80UJAOqJP8sw0Xtmian5Lcs6gVzxwkOdU
 36Po4RRGFqsG6Sq3HR+toNwKt/nHNEFkJwYcNFHdvBiXTEYYkMe6MccUxxb3i/iI
 KxB1s51zVy9t3PqjP+3J
 =i7gx
 -----END PGP SIGNATURE-----

Merge tag 'media/v3.19-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/linux-media

Pull media updates from Mauro Carvalho Chehab:
 - Two new dvb frontend drivers: mn88472 and mn88473
 - A new driver for some PCIe DVBSky cards
 - A new remote controller driver: meson-ir
 - One LIRC staging driver got rewritten and promoted to mainstream:
   igorplugusb
 - A new tuner driver (m88rs6000t)
 - The old omap2 media driver got removed from staging.  This driver
   uses an old DMA API and it is likely broken on recent kernels.
   Nobody cared enough to fix it
 - Media bus format moved to a separate header, as DRM will also use the
   definitions there
 - mem2mem_testdev were renamed to vim2m, in order to use the same
   naming convention taken by the other virtual test driver (vivid)
 - Added a new driver for coda SoC (coda-jpeg)
 - The cx88 driver got converted to use videobuf2 core
 - Make DMABUF export buffer to work with DMA Scatter/Gather and Vmalloc
   cores
 - Lots of other fixes, improvements and cleanups on the drivers.

* tag 'media/v3.19-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/linux-media: (384 commits)
  [media] mn88473: One function call less in mn88473_init() after error
  [media] mn88473: Remove uneeded check before release_firmware()
  [media] lirc_zilog: Deletion of unnecessary checks before vfree()
  [media] MAINTAINERS: Add myself as img-ir maintainer
  [media] img-ir: Don't set driver's module owner
  [media] img-ir: Depend on METAG or MIPS or COMPILE_TEST
  [media] img-ir/hw: Drop [un]register_decoder declarations
  [media] img-ir/hw: Fix potential deadlock stopping timer
  [media] img-ir/hw: Always read data to clear buffer
  [media] redrat3: ensure dma is setup properly
  [media] ddbridge: remove unneeded check before dvb_unregister_device()
  [media] si2157: One function call less in si2157_init() after error
  [media] tuners: remove uneeded checks before release_firmware()
  [media] arm: omap2: rx51-peripherals: fix build warning
  [media] stv090x: add an extra protetion against buffer overflow
  [media] stv090x: Remove an unreachable code
  [media] stv090x: Some whitespace cleanups
  [media] em28xx: checkpatch cleanup: whitespaces/new lines cleanups
  [media] si2168: add support for firmware files in new format
  [media] si2168: debug printout for firmware version
  ...
This commit is contained in:
Linus Torvalds 2014-12-11 11:49:23 -08:00
commit 2183a58803
416 changed files with 16517 additions and 13239 deletions

View file

@ -931,6 +931,35 @@ static void cx2341x_calc_audio_properties(struct cx2341x_mpeg_params *params)
}
}
/* Check for correctness of the ctrl's value based on the data from
struct v4l2_queryctrl and the available menu items. Note that
menu_items may be NULL, in that case it is ignored. */
static int v4l2_ctrl_check(struct v4l2_ext_control *ctrl, struct v4l2_queryctrl *qctrl,
const char * const *menu_items)
{
if (qctrl->flags & V4L2_CTRL_FLAG_DISABLED)
return -EINVAL;
if (qctrl->flags & V4L2_CTRL_FLAG_GRABBED)
return -EBUSY;
if (qctrl->type == V4L2_CTRL_TYPE_STRING)
return 0;
if (qctrl->type == V4L2_CTRL_TYPE_BUTTON ||
qctrl->type == V4L2_CTRL_TYPE_INTEGER64 ||
qctrl->type == V4L2_CTRL_TYPE_CTRL_CLASS)
return 0;
if (ctrl->value < qctrl->minimum || ctrl->value > qctrl->maximum)
return -ERANGE;
if (qctrl->type == V4L2_CTRL_TYPE_MENU && menu_items != NULL) {
if (menu_items[ctrl->value] == NULL ||
menu_items[ctrl->value][0] == '\0')
return -EINVAL;
}
if (qctrl->type == V4L2_CTRL_TYPE_BITMASK &&
(ctrl->value & ~qctrl->maximum))
return -ERANGE;
return 0;
}
int cx2341x_ext_ctrls(struct cx2341x_mpeg_params *params, int busy,
struct v4l2_ext_controls *ctrls, unsigned int cmd)
{

View file

@ -71,7 +71,7 @@ static inline int saa7146_wait_for_debi_done_sleep(struct saa7146_dev *dev,
if (saa7146_read(dev, MC2) & 2)
break;
if (err) {
pr_err("%s: %s timed out while waiting for registers getting programmed\n",
pr_debug("%s: %s timed out while waiting for registers getting programmed\n",
dev->name, __func__);
return -ETIMEDOUT;
}

View file

@ -107,8 +107,7 @@ int sms_ir_init(struct smscore_device_t *coredev)
void sms_ir_exit(struct smscore_device_t *coredev)
{
if (coredev->ir.dev)
rc_unregister_device(coredev->ir.dev);
rc_unregister_device(coredev->ir.dev);
sms_log("");
}

View file

@ -286,9 +286,17 @@ static const struct {
{ TUNER_ABSENT, "Xceive XC5200C"},
{ TUNER_ABSENT, "NXP 18273"},
{ TUNER_ABSENT, "Montage M88TS2022"},
/* 180-189 */
/* 180-188 */
{ TUNER_ABSENT, "NXP 18272M"},
{ TUNER_ABSENT, "NXP 18272S"},
{ TUNER_ABSENT, "Mirics MSi003"},
{ TUNER_ABSENT, "MaxLinear MxL256"},
{ TUNER_ABSENT, "SiLabs Si2158"},
{ TUNER_ABSENT, "SiLabs Si2178"},
{ TUNER_ABSENT, "SiLabs Si2157"},
{ TUNER_ABSENT, "SiLabs Si2177"},
{ TUNER_ABSENT, "ITE IT9137FN"},
};
/* Use TVEEPROM_AUDPROC_INTERNAL for those audio 'chips' that are
@ -351,6 +359,16 @@ static const struct {
{ TVEEPROM_AUDPROC_INTERNAL, "CX23887" },
{ TVEEPROM_AUDPROC_INTERNAL, "SAA7164" },
{ TVEEPROM_AUDPROC_INTERNAL, "AU8522" },
/* 45-49 */
{ TVEEPROM_AUDPROC_INTERNAL, "AVF4910B" },
{ TVEEPROM_AUDPROC_INTERNAL, "SAA7231" },
{ TVEEPROM_AUDPROC_INTERNAL, "CX23102" },
{ TVEEPROM_AUDPROC_INTERNAL, "SAA7163" },
{ TVEEPROM_AUDPROC_OTHER, "AK4113" },
/* 50-52 */
{ TVEEPROM_AUDPROC_OTHER, "CS5340" },
{ TVEEPROM_AUDPROC_OTHER, "CS8416" },
{ TVEEPROM_AUDPROC_OTHER, "CX20810" },
};
/* This list is supplied by Hauppauge. Thanks! */
@ -371,8 +389,12 @@ static const char *decoderIC[] = {
"CX25843", "CX23418", "NEC61153", "CX23885", "CX23888",
/* 35-39 */
"SAA7131", "CX25837", "CX23887", "CX23885A", "CX23887A",
/* 40-42 */
"SAA7164", "CX23885B", "AU8522"
/* 40-44 */
"SAA7164", "CX23885B", "AU8522", "ADV7401", "AVF4910B",
/* 45-49 */
"SAA7231", "CX23102", "SAA7163", "ADV7441A", "ADV7181C",
/* 50-53 */
"CX25836", "TDA9955", "TDA19977", "ADV7842"
};
static int hasRadioTuner(int tunerType)
@ -548,10 +570,10 @@ void tveeprom_hauppauge_analog(struct i2c_client *c, struct tveeprom *tvee,
tvee->serial_number =
eeprom_data[i+5] +
(eeprom_data[i+6] << 8) +
(eeprom_data[i+7] << 16);
(eeprom_data[i+7] << 16)+
(eeprom_data[i+8] << 24);
if ((eeprom_data[i + 8] & 0xf0) &&
(tvee->serial_number < 0xffffff)) {
if (eeprom_data[i + 8] == 0xf0) {
tvee->MAC_address[0] = 0x00;
tvee->MAC_address[1] = 0x0D;
tvee->MAC_address[2] = 0xFE;
@ -696,7 +718,7 @@ void tveeprom_hauppauge_analog(struct i2c_client *c, struct tveeprom *tvee,
}
}
tveeprom_info("Hauppauge model %d, rev %s, serial# %d\n",
tveeprom_info("Hauppauge model %d, rev %s, serial# %u\n",
tvee->model, tvee->rev_str, tvee->serial_number);
if (tvee->has_MAC_address == 1)
tveeprom_info("MAC address is %pM\n", tvee->MAC_address);

View file

@ -356,6 +356,7 @@
#define USB_PID_MSI_DIGI_VOX_MINI_III 0x8807
#define USB_PID_SONY_PLAYTV 0x0003
#define USB_PID_MYGICA_D689 0xd811
#define USB_PID_MYGICA_T230 0xc688
#define USB_PID_ELGATO_EYETV_DIVERSITY 0x0011
#define USB_PID_ELGATO_EYETV_DTT 0x0021
#define USB_PID_ELGATO_EYETV_DTT_2 0x003f

View file

@ -379,7 +379,9 @@ static void dvb_net_ule( struct net_device *dev, const u8 *buf, size_t buf_len )
/* Check TS error conditions: sync_byte, transport_error_indicator, scrambling_control . */
if ((ts[0] != TS_SYNC) || (ts[1] & TS_TEI) || ((ts[3] & TS_SC) != 0)) {
printk(KERN_WARNING "%lu: Invalid TS cell: SYNC %#x, TEI %u, SC %#x.\n",
priv->ts_count, ts[0], ts[1] & TS_TEI >> 7, ts[3] & 0xC0 >> 6);
priv->ts_count, ts[0],
(ts[1] & TS_TEI) >> 7,
(ts[3] & TS_SC) >> 6);
/* Drop partly decoded SNDU, reset state, resync on PUSI. */
if (priv->ule_skb) {

View file

@ -648,12 +648,15 @@ config DVB_MB86A20S
A driver for Fujitsu mb86a20s ISDB-T/ISDB-Tsb demodulator.
Say Y when you want to support this frontend.
comment "ISDB-S (satellite) & ISDB-T (terrestrial) frontends"
depends on DVB_CORE
config DVB_TC90522
tristate "Toshiba TC90522"
depends on DVB_CORE && I2C
default m if !MEDIA_SUBDRV_AUTOSELECT
help
A Toshiba TC90522 2xISDB-T + 2xISDB-S demodulator.
Toshiba TC90522 2xISDB-S 8PSK + 2xISDB-T OFDM demodulator.
Say Y when you want to support this frontend.
comment "Digital terrestrial only tuners/PLL"

View file

@ -291,6 +291,12 @@ static int af9033_init(struct dvb_frontend *fe)
if (clock_adc_lut[i].clock == dev->cfg.clock)
break;
}
if (i == ARRAY_SIZE(clock_adc_lut)) {
dev_err(&dev->client->dev,
"Couldn't find ADC config for clock=%d\n",
dev->cfg.clock);
goto err;
}
adc_cw = af9033_div(dev, clock_adc_lut[i].adc, 1000000ul, 19ul);
buf[0] = (adc_cw >> 0) & 0xff;
@ -580,7 +586,15 @@ static int af9033_set_frontend(struct dvb_frontend *fe)
break;
}
}
ret = af9033_wr_regs(dev, 0x800001,
if (i == ARRAY_SIZE(coeff_lut)) {
dev_err(&dev->client->dev,
"Couldn't find LUT config for clock=%d\n",
dev->cfg.clock);
ret = -EINVAL;
goto err;
}
ret = af9033_wr_regs(dev, 0x800001,
coeff_lut[i].val, sizeof(coeff_lut[i].val));
}
@ -592,6 +606,13 @@ static int af9033_set_frontend(struct dvb_frontend *fe)
if (clock_adc_lut[i].clock == dev->cfg.clock)
break;
}
if (i == ARRAY_SIZE(clock_adc_lut)) {
dev_err(&dev->client->dev,
"Couldn't find ADC clock for clock=%d\n",
dev->cfg.clock);
ret = -EINVAL;
goto err;
}
adc_freq = clock_adc_lut[i].adc;
/* get used IF frequency */
@ -849,29 +870,97 @@ static int af9033_read_snr(struct dvb_frontend *fe, u16 *snr)
{
struct af9033_dev *dev = fe->demodulator_priv;
struct dtv_frontend_properties *c = &dev->fe.dtv_property_cache;
int ret;
u8 u8tmp;
/* use DVBv5 CNR */
if (c->cnr.stat[0].scale == FE_SCALE_DECIBEL)
*snr = div_s64(c->cnr.stat[0].svalue, 100); /* 1000x => 10x */
else
if (c->cnr.stat[0].scale == FE_SCALE_DECIBEL) {
/* Return 0.1 dB for AF9030 and 0-0xffff for IT9130. */
if (dev->is_af9035) {
/* 1000x => 10x (0.1 dB) */
*snr = div_s64(c->cnr.stat[0].svalue, 100);
} else {
/* 1000x => 1x (1 dB) */
*snr = div_s64(c->cnr.stat[0].svalue, 1000);
/* read current modulation */
ret = af9033_rd_reg(dev, 0x80f903, &u8tmp);
if (ret)
goto err;
/* scale value to 0x0000-0xffff */
switch ((u8tmp >> 0) & 3) {
case 0:
*snr = *snr * 0xffff / 23;
break;
case 1:
*snr = *snr * 0xffff / 26;
break;
case 2:
*snr = *snr * 0xffff / 32;
break;
default:
goto err;
}
}
} else {
*snr = 0;
}
return 0;
err:
dev_dbg(&dev->client->dev, "failed=%d\n", ret);
return ret;
}
static int af9033_read_signal_strength(struct dvb_frontend *fe, u16 *strength)
{
struct af9033_dev *dev = fe->demodulator_priv;
int ret;
u8 strength2;
struct dtv_frontend_properties *c = &dev->fe.dtv_property_cache;
int ret, tmp, power_real;
u8 u8tmp, gain_offset, buf[7];
/* read signal strength of 0-100 scale */
ret = af9033_rd_reg(dev, 0x800048, &strength2);
if (ret < 0)
goto err;
if (dev->is_af9035) {
/* read signal strength of 0-100 scale */
ret = af9033_rd_reg(dev, 0x800048, &u8tmp);
if (ret < 0)
goto err;
/* scale value to 0x0000-0xffff */
*strength = strength2 * 0xffff / 100;
/* scale value to 0x0000-0xffff */
*strength = u8tmp * 0xffff / 100;
} else {
ret = af9033_rd_reg(dev, 0x8000f7, &u8tmp);
if (ret < 0)
goto err;
ret = af9033_rd_regs(dev, 0x80f900, buf, 7);
if (ret < 0)
goto err;
if (c->frequency <= 300000000)
gain_offset = 7; /* VHF */
else
gain_offset = 4; /* UHF */
power_real = (u8tmp - 100 - gain_offset) -
power_reference[((buf[3] >> 0) & 3)][((buf[6] >> 0) & 7)];
if (power_real < -15)
tmp = 0;
else if ((power_real >= -15) && (power_real < 0))
tmp = (2 * (power_real + 15)) / 3;
else if ((power_real >= 0) && (power_real < 20))
tmp = 4 * power_real + 10;
else if ((power_real >= 20) && (power_real < 35))
tmp = (2 * (power_real - 20)) / 3 + 90;
else
tmp = 100;
/* scale value to 0x0000-0xffff */
*strength = tmp * 0xffff / 100;
}
return 0;
@ -1011,6 +1100,33 @@ static void af9033_stat_work(struct work_struct *work)
snr_val = (buf[2] << 16) | (buf[1] << 8) | (buf[0] << 0);
/* read superframe number */
ret = af9033_rd_reg(dev, 0x80f78b, &u8tmp);
if (ret)
goto err;
if (u8tmp)
snr_val /= u8tmp;
/* read current transmission mode */
ret = af9033_rd_reg(dev, 0x80f900, &u8tmp);
if (ret)
goto err;
switch ((u8tmp >> 0) & 3) {
case 0:
snr_val *= 4;
break;
case 1:
snr_val *= 1;
break;
case 2:
snr_val *= 2;
break;
default:
goto err_schedule_delayed_work;
}
/* read current modulation */
ret = af9033_rd_reg(dev, 0x80f903, &u8tmp);
if (ret)

View file

@ -181,7 +181,10 @@ static const struct val_snr qam64_snr_lut[] = {
{ 0x05570d, 26 },
{ 0x059feb, 27 },
{ 0x05bf38, 28 },
{ 0xffffff, 29 },
{ 0x05f78f, 29 },
{ 0x0612c3, 30 },
{ 0x0626be, 31 },
{ 0xffffff, 32 },
};
static const struct reg_val ofsm_init[] = {
@ -2051,4 +2054,10 @@ static const struct reg_val tuner_init_it9135_62[] = {
{ 0x80fd8b, 0x00 },
};
/* NorDig power reference table */
static const int power_reference[][5] = {
{-93, -91, -90, -89, -88}, /* QPSK 1/2 ~ 7/8 */
{-87, -85, -84, -83, -82}, /* 16QAM 1/2 ~ 7/8 */
{-82, -80, -78, -77, -76}, /* 64QAM 1/2 ~ 7/8 */
};
#endif /* AF9033_PRIV_H */

View file

@ -29,6 +29,7 @@
#include "au8522_priv.h"
static int debug;
static int zv_mode = 1; /* default to on */
#define dprintk(arg...)\
do { if (debug)\
@ -469,6 +470,87 @@ static struct {
{ 0x8526, 0x01 },
};
static struct {
u16 reg;
u16 data;
} QAM256_mod_tab_zv_mode[] = {
{ 0x80a3, 0x09 },
{ 0x80a4, 0x00 },
{ 0x8081, 0xc4 },
{ 0x80a5, 0x40 },
{ 0x80b5, 0xfb },
{ 0x80b6, 0x8e },
{ 0x80b7, 0x39 },
{ 0x80aa, 0x77 },
{ 0x80ad, 0x77 },
{ 0x80a6, 0x67 },
{ 0x8262, 0x20 },
{ 0x821c, 0x30 },
{ 0x80b8, 0x3e },
{ 0x80b9, 0xf0 },
{ 0x80ba, 0x01 },
{ 0x80bb, 0x18 },
{ 0x80bc, 0x50 },
{ 0x80bd, 0x00 },
{ 0x80be, 0xea },
{ 0x80bf, 0xef },
{ 0x80c0, 0xfc },
{ 0x80c1, 0xbd },
{ 0x80c2, 0x1f },
{ 0x80c3, 0xfc },
{ 0x80c4, 0xdd },
{ 0x80c5, 0xaf },
{ 0x80c6, 0x00 },
{ 0x80c7, 0x38 },
{ 0x80c8, 0x30 },
{ 0x80c9, 0x05 },
{ 0x80ca, 0x4a },
{ 0x80cb, 0xd0 },
{ 0x80cc, 0x01 },
{ 0x80cd, 0xd9 },
{ 0x80ce, 0x6f },
{ 0x80cf, 0xf9 },
{ 0x80d0, 0x70 },
{ 0x80d1, 0xdf },
{ 0x80d2, 0xf7 },
{ 0x80d3, 0xc2 },
{ 0x80d4, 0xdf },
{ 0x80d5, 0x02 },
{ 0x80d6, 0x9a },
{ 0x80d7, 0xd0 },
{ 0x8250, 0x0d },
{ 0x8251, 0xcd },
{ 0x8252, 0xe0 },
{ 0x8253, 0x05 },
{ 0x8254, 0xa7 },
{ 0x8255, 0xff },
{ 0x8256, 0xed },
{ 0x8257, 0x5b },
{ 0x8258, 0xae },
{ 0x8259, 0xe6 },
{ 0x825a, 0x3d },
{ 0x825b, 0x0f },
{ 0x825c, 0x0d },
{ 0x825d, 0xea },
{ 0x825e, 0xf2 },
{ 0x825f, 0x51 },
{ 0x8260, 0xf5 },
{ 0x8261, 0x06 },
{ 0x821a, 0x01 },
{ 0x8546, 0x40 },
{ 0x8210, 0x26 },
{ 0x8211, 0xf6 },
{ 0x8212, 0x84 },
{ 0x8213, 0x02 },
{ 0x8502, 0x01 },
{ 0x8121, 0x04 },
{ 0x8122, 0x04 },
{ 0x852e, 0x10 },
{ 0x80a4, 0xca },
{ 0x80a7, 0x40 },
{ 0x8526, 0x01 },
};
static int au8522_enable_modulation(struct dvb_frontend *fe,
fe_modulation_t m)
{
@ -495,12 +577,23 @@ static int au8522_enable_modulation(struct dvb_frontend *fe,
au8522_set_if(fe, state->config->qam_if);
break;
case QAM_256:
dprintk("%s() QAM 256\n", __func__);
for (i = 0; i < ARRAY_SIZE(QAM256_mod_tab); i++)
au8522_writereg(state,
QAM256_mod_tab[i].reg,
QAM256_mod_tab[i].data);
au8522_set_if(fe, state->config->qam_if);
if (zv_mode) {
dprintk("%s() QAM 256 (zv_mode)\n", __func__);
for (i = 0; i < ARRAY_SIZE(QAM256_mod_tab_zv_mode); i++)
au8522_writereg(state,
QAM256_mod_tab_zv_mode[i].reg,
QAM256_mod_tab_zv_mode[i].data);
au8522_set_if(fe, state->config->qam_if);
msleep(100);
au8522_writereg(state, 0x821a, 0x00);
} else {
dprintk("%s() QAM 256\n", __func__);
for (i = 0; i < ARRAY_SIZE(QAM256_mod_tab); i++)
au8522_writereg(state,
QAM256_mod_tab[i].reg,
QAM256_mod_tab[i].data);
au8522_set_if(fe, state->config->qam_if);
}
break;
default:
dprintk("%s() Invalid modulation\n", __func__);
@ -537,7 +630,12 @@ static int au8522_set_frontend(struct dvb_frontend *fe)
return ret;
/* Allow the tuner to settle */
msleep(100);
if (zv_mode) {
dprintk("%s() increase tuner settling time for zv_mode\n",
__func__);
msleep(250);
} else
msleep(100);
au8522_enable_modulation(fe, c->modulation);
@ -823,6 +921,11 @@ static struct dvb_frontend_ops au8522_ops = {
module_param(debug, int, 0644);
MODULE_PARM_DESC(debug, "Enable verbose debug messages");
module_param(zv_mode, int, 0644);
MODULE_PARM_DESC(zv_mode, "Turn on/off ZeeVee modulator compatability mode (default:on).\n"
"\t\ton - modified AU8522 QAM256 initialization.\n"
"\t\tProvides faster lock when using ZeeVee modulator based sources");
MODULE_DESCRIPTION("Auvitek AU8522 QAM-B/ATSC Demodulator driver");
MODULE_AUTHOR("Steven Toth");
MODULE_LICENSE("GPL");

View file

@ -169,6 +169,9 @@ static int cx22700_set_tps(struct cx22700_state *state,
cx22700_writereg (state, 0x04, val);
if (p->code_rate_HP - FEC_1_2 >= sizeof(fec_tab) ||
p->code_rate_LP - FEC_1_2 >= sizeof(fec_tab))
return -EINVAL;
val = fec_tab[p->code_rate_HP - FEC_1_2] << 3;
val |= fec_tab[p->code_rate_LP - FEC_1_2];

View file

@ -177,47 +177,45 @@ static int cx24110_set_inversion (struct cx24110_state* state, fe_spectral_inver
return 0;
}
static int cx24110_set_fec (struct cx24110_state* state, fe_code_rate_t fec)
static int cx24110_set_fec(struct cx24110_state* state, fe_code_rate_t fec)
{
/* fixme (low): error handling */
static const int rate[]={-1,1,2,3,5,7,-1};
static const int g1[]={-1,0x01,0x02,0x05,0x15,0x45,-1};
static const int g2[]={-1,0x01,0x03,0x06,0x1a,0x7a,-1};
static const int rate[FEC_AUTO] = {-1, 1, 2, 3, 5, 7, -1};
static const int g1[FEC_AUTO] = {-1, 0x01, 0x02, 0x05, 0x15, 0x45, -1};
static const int g2[FEC_AUTO] = {-1, 0x01, 0x03, 0x06, 0x1a, 0x7a, -1};
/* Well, the AutoAcq engine of the cx24106 and 24110 automatically
searches all enabled viterbi rates, and can handle non-standard
rates as well. */
if (fec>FEC_AUTO)
fec=FEC_AUTO;
if (fec > FEC_AUTO)
fec = FEC_AUTO;
if (fec==FEC_AUTO) { /* (re-)establish AutoAcq behaviour */
cx24110_writereg(state,0x37,cx24110_readreg(state,0x37)&0xdf);
if (fec == FEC_AUTO) { /* (re-)establish AutoAcq behaviour */
cx24110_writereg(state, 0x37, cx24110_readreg(state, 0x37) & 0xdf);
/* clear AcqVitDis bit */
cx24110_writereg(state,0x18,0xae);
cx24110_writereg(state, 0x18, 0xae);
/* allow all DVB standard code rates */
cx24110_writereg(state,0x05,(cx24110_readreg(state,0x05)&0xf0)|0x3);
cx24110_writereg(state, 0x05, (cx24110_readreg(state, 0x05) & 0xf0) | 0x3);
/* set nominal Viterbi rate 3/4 */
cx24110_writereg(state,0x22,(cx24110_readreg(state,0x22)&0xf0)|0x3);
cx24110_writereg(state, 0x22, (cx24110_readreg(state, 0x22) & 0xf0) | 0x3);
/* set current Viterbi rate 3/4 */
cx24110_writereg(state,0x1a,0x05); cx24110_writereg(state,0x1b,0x06);
cx24110_writereg(state, 0x1a, 0x05);
cx24110_writereg(state, 0x1b, 0x06);
/* set the puncture registers for code rate 3/4 */
return 0;
} else {
cx24110_writereg(state,0x37,cx24110_readreg(state,0x37)|0x20);
cx24110_writereg(state, 0x37, cx24110_readreg(state, 0x37) | 0x20);
/* set AcqVitDis bit */
if(rate[fec]>0) {
cx24110_writereg(state,0x05,(cx24110_readreg(state,0x05)&0xf0)|rate[fec]);
/* set nominal Viterbi rate */
cx24110_writereg(state,0x22,(cx24110_readreg(state,0x22)&0xf0)|rate[fec]);
/* set current Viterbi rate */
cx24110_writereg(state,0x1a,g1[fec]);
cx24110_writereg(state,0x1b,g2[fec]);
/* not sure if this is the right way: I always used AutoAcq mode */
} else
return -EOPNOTSUPP;
/* fixme (low): which is the correct return code? */
if (rate[fec] < 0)
return -EINVAL;
cx24110_writereg(state, 0x05, (cx24110_readreg(state, 0x05) & 0xf0) | rate[fec]);
/* set nominal Viterbi rate */
cx24110_writereg(state, 0x22, (cx24110_readreg(state, 0x22) & 0xf0) | rate[fec]);
/* set current Viterbi rate */
cx24110_writereg(state, 0x1a, g1[fec]);
cx24110_writereg(state, 0x1b, g2[fec]);
/* not sure if this is the right way: I always used AutoAcq mode */
}
return 0;
}

View file

@ -459,7 +459,7 @@ static int cx24117_firmware_ondemand(struct dvb_frontend *fe)
if (state->priv->skip_fw_load)
return 0;
/* check if firmware if already running */
/* check if firmware is already running */
if (cx24117_readreg(state, 0xeb) != 0xa) {
/* Load firmware */
/* request the firmware, this will block until loaded */

View file

@ -1780,7 +1780,7 @@ static u32 interpolate_value(u32 value, struct linear_segments *segments,
}
/* FIXME: may require changes - this one was borrowed from dib8000 */
static u32 dib7000p_get_time_us(struct dvb_frontend *demod, int layer)
static u32 dib7000p_get_time_us(struct dvb_frontend *demod)
{
struct dtv_frontend_properties *c = &demod->dtv_property_cache;
u64 time_us, tmp64;
@ -1881,7 +1881,6 @@ static int dib7000p_get_stats(struct dvb_frontend *demod, fe_status_t stat)
{
struct dib7000p_state *state = demod->demodulator_priv;
struct dtv_frontend_properties *c = &demod->dtv_property_cache;
int i;
int show_per_stats = 0;
u32 time_us = 0, val, snr;
u64 blocks, ucb;
@ -1935,7 +1934,7 @@ static int dib7000p_get_stats(struct dvb_frontend *demod, fe_status_t stat)
/* Estimate the number of packets based on bitrate */
if (!time_us)
time_us = dib7000p_get_time_us(demod, -1);
time_us = dib7000p_get_time_us(demod);
if (time_us) {
blocks = 1250000ULL * 1000000ULL;
@ -1949,7 +1948,7 @@ static int dib7000p_get_stats(struct dvb_frontend *demod, fe_status_t stat)
/* Get post-BER measures */
if (time_after(jiffies, state->ber_jiffies_stats)) {
time_us = dib7000p_get_time_us(demod, -1);
time_us = dib7000p_get_time_us(demod);
state->ber_jiffies_stats = jiffies + msecs_to_jiffies((time_us + 500) / 1000);
dprintk("Next all layers stats available in %u us.", time_us);
@ -1969,7 +1968,7 @@ static int dib7000p_get_stats(struct dvb_frontend *demod, fe_status_t stat)
c->block_error.stat[0].scale = FE_SCALE_COUNTER;
c->block_error.stat[0].uvalue += val;
time_us = dib7000p_get_time_us(demod, i);
time_us = dib7000p_get_time_us(demod);
if (time_us) {
blocks = 1250000ULL * 1000000ULL;
do_div(blocks, time_us * 8 * 204);

View file

@ -12255,8 +12255,7 @@ static void drx39xxj_release(struct dvb_frontend *fe)
kfree(demod->my_ext_attr);
kfree(demod->my_common_attr);
kfree(demod->my_i2c_dev_addr);
if (demod->firmware)
release_firmware(demod->firmware);
release_firmware(demod->firmware);
kfree(demod);
kfree(state);
}

View file

@ -166,9 +166,9 @@ static unsigned int debug;
module_param(debug, int, 0644);
MODULE_PARM_DESC(debug, "enable debug messages");
#define dprintk(level, fmt, arg...) do { \
if (debug >= level) \
pr_debug(fmt, ##arg); \
#define dprintk(level, fmt, arg...) do { \
if (debug >= level) \
printk(KERN_DEBUG KBUILD_MODNAME ": %s " fmt, __func__, ##arg); \
} while (0)
@ -6310,8 +6310,7 @@ static void drxk_release(struct dvb_frontend *fe)
struct drxk_state *state = fe->demodulator_priv;
dprintk(1, "\n");
if (state->fw)
release_firmware(state->fw);
release_firmware(state->fw);
kfree(state);
}

View file

@ -1,5 +1,5 @@
/*
* Montage M88DS3103 demodulator driver
* Montage M88DS3103/M88RS6000 demodulator driver
*
* Copyright (C) 2013 Antti Palosaari <crope@iki.fi>
*
@ -162,7 +162,7 @@ static int m88ds3103_wr_reg_val_tab(struct m88ds3103_priv *priv,
dev_dbg(&priv->i2c->dev, "%s: tab_len=%d\n", __func__, tab_len);
if (tab_len > 83) {
if (tab_len > 86) {
ret = -EINVAL;
goto err;
}
@ -245,9 +245,9 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
struct dtv_frontend_properties *c = &fe->dtv_property_cache;
int ret, len;
const struct m88ds3103_reg_val *init;
u8 u8tmp, u8tmp1, u8tmp2;
u8 buf[2];
u16 u16tmp, divide_ratio;
u8 u8tmp, u8tmp1 = 0, u8tmp2 = 0; /* silence compiler warning */
u8 buf[3];
u16 u16tmp, divide_ratio = 0;
u32 tuner_frequency, target_mclk;
s32 s32tmp;
@ -262,6 +262,22 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
goto err;
}
/* reset */
ret = m88ds3103_wr_reg(priv, 0x07, 0x80);
if (ret)
goto err;
ret = m88ds3103_wr_reg(priv, 0x07, 0x00);
if (ret)
goto err;
/* Disable demod clock path */
if (priv->chip_id == M88RS6000_CHIP_ID) {
ret = m88ds3103_wr_reg(priv, 0x06, 0xe0);
if (ret)
goto err;
}
/* program tuner */
if (fe->ops.tuner_ops.set_params) {
ret = fe->ops.tuner_ops.set_params(fe);
@ -282,14 +298,73 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
tuner_frequency = c->frequency;
}
/* reset */
ret = m88ds3103_wr_reg(priv, 0x07, 0x80);
if (ret)
goto err;
/* select M88RS6000 demod main mclk and ts mclk from tuner die. */
if (priv->chip_id == M88RS6000_CHIP_ID) {
if (c->symbol_rate > 45010000)
priv->mclk_khz = 110250;
else
priv->mclk_khz = 96000;
ret = m88ds3103_wr_reg(priv, 0x07, 0x00);
if (ret)
goto err;
if (c->delivery_system == SYS_DVBS)
target_mclk = 96000;
else
target_mclk = 144000;
/* Enable demod clock path */
ret = m88ds3103_wr_reg(priv, 0x06, 0x00);
if (ret)
goto err;
usleep_range(10000, 20000);
} else {
/* set M88DS3103 mclk and ts mclk. */
priv->mclk_khz = 96000;
switch (priv->cfg->ts_mode) {
case M88DS3103_TS_SERIAL:
case M88DS3103_TS_SERIAL_D7:
target_mclk = priv->cfg->ts_clk;
break;
case M88DS3103_TS_PARALLEL:
case M88DS3103_TS_CI:
if (c->delivery_system == SYS_DVBS)
target_mclk = 96000;
else {
if (c->symbol_rate < 18000000)
target_mclk = 96000;
else if (c->symbol_rate < 28000000)
target_mclk = 144000;
else
target_mclk = 192000;
}
break;
default:
dev_dbg(&priv->i2c->dev, "%s: invalid ts_mode\n",
__func__);
ret = -EINVAL;
goto err;
}
switch (target_mclk) {
case 96000:
u8tmp1 = 0x02; /* 0b10 */
u8tmp2 = 0x01; /* 0b01 */
break;
case 144000:
u8tmp1 = 0x00; /* 0b00 */
u8tmp2 = 0x01; /* 0b01 */
break;
case 192000:
u8tmp1 = 0x03; /* 0b11 */
u8tmp2 = 0x00; /* 0b00 */
break;
}
ret = m88ds3103_wr_reg_mask(priv, 0x22, u8tmp1 << 6, 0xc0);
if (ret)
goto err;
ret = m88ds3103_wr_reg_mask(priv, 0x24, u8tmp2 << 6, 0xc0);
if (ret)
goto err;
}
ret = m88ds3103_wr_reg(priv, 0xb2, 0x01);
if (ret)
@ -301,36 +376,21 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
switch (c->delivery_system) {
case SYS_DVBS:
len = ARRAY_SIZE(m88ds3103_dvbs_init_reg_vals);
init = m88ds3103_dvbs_init_reg_vals;
target_mclk = 96000;
if (priv->chip_id == M88RS6000_CHIP_ID) {
len = ARRAY_SIZE(m88rs6000_dvbs_init_reg_vals);
init = m88rs6000_dvbs_init_reg_vals;
} else {
len = ARRAY_SIZE(m88ds3103_dvbs_init_reg_vals);
init = m88ds3103_dvbs_init_reg_vals;
}
break;
case SYS_DVBS2:
len = ARRAY_SIZE(m88ds3103_dvbs2_init_reg_vals);
init = m88ds3103_dvbs2_init_reg_vals;
switch (priv->cfg->ts_mode) {
case M88DS3103_TS_SERIAL:
case M88DS3103_TS_SERIAL_D7:
if (c->symbol_rate < 18000000)
target_mclk = 96000;
else
target_mclk = 144000;
break;
case M88DS3103_TS_PARALLEL:
case M88DS3103_TS_CI:
if (c->symbol_rate < 18000000)
target_mclk = 96000;
else if (c->symbol_rate < 28000000)
target_mclk = 144000;
else
target_mclk = 192000;
break;
default:
dev_dbg(&priv->i2c->dev, "%s: invalid ts_mode\n",
__func__);
ret = -EINVAL;
goto err;
if (priv->chip_id == M88RS6000_CHIP_ID) {
len = ARRAY_SIZE(m88rs6000_dvbs2_init_reg_vals);
init = m88rs6000_dvbs2_init_reg_vals;
} else {
len = ARRAY_SIZE(m88ds3103_dvbs2_init_reg_vals);
init = m88ds3103_dvbs2_init_reg_vals;
}
break;
default:
@ -347,7 +407,30 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
goto err;
}
u8tmp1 = 0; /* silence compiler warning */
if (priv->chip_id == M88RS6000_CHIP_ID) {
if ((c->delivery_system == SYS_DVBS2)
&& ((c->symbol_rate / 1000) <= 5000)) {
ret = m88ds3103_wr_reg(priv, 0xc0, 0x04);
if (ret)
goto err;
buf[0] = 0x09;
buf[1] = 0x22;
buf[2] = 0x88;
ret = m88ds3103_wr_regs(priv, 0x8a, buf, 3);
if (ret)
goto err;
}
ret = m88ds3103_wr_reg_mask(priv, 0x9d, 0x08, 0x08);
if (ret)
goto err;
ret = m88ds3103_wr_reg(priv, 0xf1, 0x01);
if (ret)
goto err;
ret = m88ds3103_wr_reg_mask(priv, 0x30, 0x80, 0x80);
if (ret)
goto err;
}
switch (priv->cfg->ts_mode) {
case M88DS3103_TS_SERIAL:
u8tmp1 = 0x00;
@ -383,16 +466,15 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
ret = m88ds3103_wr_reg_mask(priv, 0x29, u8tmp1, 0x20);
if (ret)
goto err;
}
if (priv->cfg->ts_clk) {
divide_ratio = DIV_ROUND_UP(target_mclk, priv->cfg->ts_clk);
u8tmp1 = divide_ratio / 2;
u8tmp2 = DIV_ROUND_UP(divide_ratio, 2);
} else {
divide_ratio = 0;
u8tmp1 = 0;
u8tmp2 = 0;
break;
default:
if (priv->cfg->ts_clk) {
divide_ratio = DIV_ROUND_UP(target_mclk, priv->cfg->ts_clk);
u8tmp1 = divide_ratio / 2;
u8tmp2 = DIV_ROUND_UP(divide_ratio, 2);
}
}
dev_dbg(&priv->i2c->dev,
@ -420,29 +502,6 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
if (ret)
goto err;
switch (target_mclk) {
case 96000:
u8tmp1 = 0x02; /* 0b10 */
u8tmp2 = 0x01; /* 0b01 */
break;
case 144000:
u8tmp1 = 0x00; /* 0b00 */
u8tmp2 = 0x01; /* 0b01 */
break;
case 192000:
u8tmp1 = 0x03; /* 0b11 */
u8tmp2 = 0x00; /* 0b00 */
break;
}
ret = m88ds3103_wr_reg_mask(priv, 0x22, u8tmp1 << 6, 0xc0);
if (ret)
goto err;
ret = m88ds3103_wr_reg_mask(priv, 0x24, u8tmp2 << 6, 0xc0);
if (ret)
goto err;
if (c->symbol_rate <= 3000000)
u8tmp = 0x20;
else if (c->symbol_rate <= 10000000)
@ -466,7 +525,7 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
if (ret)
goto err;
u16tmp = DIV_ROUND_CLOSEST((c->symbol_rate / 1000) << 15, M88DS3103_MCLK_KHZ / 2);
u16tmp = DIV_ROUND_CLOSEST((c->symbol_rate / 1000) << 15, priv->mclk_khz / 2);
buf[0] = (u16tmp >> 0) & 0xff;
buf[1] = (u16tmp >> 8) & 0xff;
ret = m88ds3103_wr_regs(priv, 0x61, buf, 2);
@ -489,7 +548,7 @@ static int m88ds3103_set_frontend(struct dvb_frontend *fe)
(tuner_frequency - c->frequency));
s32tmp = 0x10000 * (tuner_frequency - c->frequency);
s32tmp = DIV_ROUND_CLOSEST(s32tmp, M88DS3103_MCLK_KHZ);
s32tmp = DIV_ROUND_CLOSEST(s32tmp, priv->mclk_khz);
if (s32tmp < 0)
s32tmp += 0x10000;
@ -520,7 +579,7 @@ static int m88ds3103_init(struct dvb_frontend *fe)
struct m88ds3103_priv *priv = fe->demodulator_priv;
int ret, len, remaining;
const struct firmware *fw = NULL;
u8 *fw_file = M88DS3103_FIRMWARE;
u8 *fw_file;
u8 u8tmp;
dev_dbg(&priv->i2c->dev, "%s:\n", __func__);
@ -541,15 +600,6 @@ static int m88ds3103_init(struct dvb_frontend *fe)
if (ret)
goto err;
/* reset */
ret = m88ds3103_wr_reg(priv, 0x07, 0x60);
if (ret)
goto err;
ret = m88ds3103_wr_reg(priv, 0x07, 0x00);
if (ret)
goto err;
/* firmware status */
ret = m88ds3103_rd_reg(priv, 0xb9, &u8tmp);
if (ret)
@ -560,10 +610,23 @@ static int m88ds3103_init(struct dvb_frontend *fe)
if (u8tmp)
goto skip_fw_download;
/* global reset, global diseqc reset, golbal fec reset */
ret = m88ds3103_wr_reg(priv, 0x07, 0xe0);
if (ret)
goto err;
ret = m88ds3103_wr_reg(priv, 0x07, 0x00);
if (ret)
goto err;
/* cold state - try to download firmware */
dev_info(&priv->i2c->dev, "%s: found a '%s' in cold state\n",
KBUILD_MODNAME, m88ds3103_ops.info.name);
if (priv->chip_id == M88RS6000_CHIP_ID)
fw_file = M88RS6000_FIRMWARE;
else
fw_file = M88DS3103_FIRMWARE;
/* request the firmware, this will block and timeout */
ret = request_firmware(&fw, fw_file, priv->i2c->dev.parent);
if (ret) {
@ -577,7 +640,7 @@ static int m88ds3103_init(struct dvb_frontend *fe)
ret = m88ds3103_wr_reg(priv, 0xb2, 0x01);
if (ret)
goto err;
goto error_fw_release;
for (remaining = fw->size; remaining > 0;
remaining -= (priv->cfg->i2c_wr_max - 1)) {
@ -591,13 +654,13 @@ static int m88ds3103_init(struct dvb_frontend *fe)
dev_err(&priv->i2c->dev,
"%s: firmware download failed=%d\n",
KBUILD_MODNAME, ret);
goto err;
goto error_fw_release;
}
}
ret = m88ds3103_wr_reg(priv, 0xb2, 0x00);
if (ret)
goto err;
goto error_fw_release;
release_firmware(fw);
fw = NULL;
@ -623,10 +686,10 @@ skip_fw_download:
priv->warm = true;
return 0;
err:
if (fw)
release_firmware(fw);
error_fw_release:
release_firmware(fw);
err:
dev_dbg(&priv->i2c->dev, "%s: failed=%d\n", __func__, ret);
return ret;
}
@ -635,13 +698,18 @@ static int m88ds3103_sleep(struct dvb_frontend *fe)
{
struct m88ds3103_priv *priv = fe->demodulator_priv;
int ret;
u8 u8tmp;
dev_dbg(&priv->i2c->dev, "%s:\n", __func__);
priv->delivery_system = SYS_UNDEFINED;
/* TS Hi-Z */
ret = m88ds3103_wr_reg_mask(priv, 0x27, 0x00, 0x01);
if (priv->chip_id == M88RS6000_CHIP_ID)
u8tmp = 0x29;
else
u8tmp = 0x27;
ret = m88ds3103_wr_reg_mask(priv, u8tmp, 0x00, 0x01);
if (ret)
goto err;
@ -830,7 +898,7 @@ static int m88ds3103_get_frontend(struct dvb_frontend *fe)
goto err;
c->symbol_rate = 1ull * ((buf[1] << 8) | (buf[0] << 0)) *
M88DS3103_MCLK_KHZ * 1000 / 0x10000;
priv->mclk_khz * 1000 / 0x10000;
return 0;
err:
@ -1310,18 +1378,22 @@ struct dvb_frontend *m88ds3103_attach(const struct m88ds3103_config *cfg,
priv->i2c = i2c;
mutex_init(&priv->i2c_mutex);
ret = m88ds3103_rd_reg(priv, 0x01, &chip_id);
/* 0x00: chip id[6:0], 0x01: chip ver[7:0], 0x02: chip ver[15:8] */
ret = m88ds3103_rd_reg(priv, 0x00, &chip_id);
if (ret)
goto err;
dev_dbg(&priv->i2c->dev, "%s: chip_id=%02x\n", __func__, chip_id);
chip_id >>= 1;
dev_info(&priv->i2c->dev, "%s: chip_id=%02x\n", __func__, chip_id);
switch (chip_id) {
case 0xd0:
case M88RS6000_CHIP_ID:
case M88DS3103_CHIP_ID:
break;
default:
goto err;
}
priv->chip_id = chip_id;
switch (priv->cfg->clock_out) {
case M88DS3103_CLOCK_OUT_DISABLED:
@ -1337,6 +1409,11 @@ struct dvb_frontend *m88ds3103_attach(const struct m88ds3103_config *cfg,
goto err;
}
/* 0x29 register is defined differently for m88rs6000. */
/* set internal tuner address to 0x21 */
if (chip_id == M88RS6000_CHIP_ID)
u8tmp = 0x00;
ret = m88ds3103_wr_reg(priv, 0x29, u8tmp);
if (ret)
goto err;
@ -1364,6 +1441,9 @@ struct dvb_frontend *m88ds3103_attach(const struct m88ds3103_config *cfg,
/* create dvb_frontend */
memcpy(&priv->fe.ops, &m88ds3103_ops, sizeof(struct dvb_frontend_ops));
if (priv->chip_id == M88RS6000_CHIP_ID)
strncpy(priv->fe.ops.info.name,
"Montage M88RS6000", sizeof(priv->fe.ops.info.name));
priv->fe.demodulator_priv = priv;
return &priv->fe;
@ -1423,3 +1503,4 @@ MODULE_AUTHOR("Antti Palosaari <[email protected]>");
MODULE_DESCRIPTION("Montage M88DS3103 DVB-S/S2 demodulator driver");
MODULE_LICENSE("GPL");
MODULE_FIRMWARE(M88DS3103_FIRMWARE);
MODULE_FIRMWARE(M88RS6000_FIRMWARE);

View file

@ -25,7 +25,10 @@
#include <linux/math64.h>
#define M88DS3103_FIRMWARE "dvb-demod-m88ds3103.fw"
#define M88RS6000_FIRMWARE "dvb-demod-m88rs6000.fw"
#define M88DS3103_MCLK_KHZ 96000
#define M88RS6000_CHIP_ID 0x74
#define M88DS3103_CHIP_ID 0x70
struct m88ds3103_priv {
struct i2c_adapter *i2c;
@ -38,6 +41,10 @@ struct m88ds3103_priv {
u32 ber;
bool warm; /* FW running */
struct i2c_adapter *i2c_adapter;
/* auto detect chip id to do different config */
u8 chip_id;
/* main mclk is calculated for M88RS6000 dynamically */
u32 mclk_khz;
};
struct m88ds3103_reg_val {
@ -214,4 +221,178 @@ static const struct m88ds3103_reg_val m88ds3103_dvbs2_init_reg_vals[] = {
{0xb8, 0x00},
};
static const struct m88ds3103_reg_val m88rs6000_dvbs_init_reg_vals[] = {
{0x23, 0x07},
{0x08, 0x03},
{0x0c, 0x02},
{0x20, 0x00},
{0x21, 0x54},
{0x25, 0x82},
{0x27, 0x31},
{0x30, 0x08},
{0x31, 0x40},
{0x32, 0x32},
{0x33, 0x35},
{0x35, 0xff},
{0x3a, 0x00},
{0x37, 0x10},
{0x38, 0x10},
{0x39, 0x02},
{0x42, 0x60},
{0x4a, 0x80},
{0x4b, 0x04},
{0x4d, 0x91},
{0x5d, 0xc8},
{0x50, 0x36},
{0x51, 0x36},
{0x52, 0x36},
{0x53, 0x36},
{0x63, 0x0f},
{0x64, 0x30},
{0x65, 0x40},
{0x68, 0x26},
{0x69, 0x4c},
{0x70, 0x20},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x40},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x60},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x80},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0xa0},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x1f},
{0x76, 0x38},
{0x77, 0xa6},
{0x78, 0x0c},
{0x79, 0x80},
{0x7f, 0x14},
{0x7c, 0x00},
{0xae, 0x82},
{0x80, 0x64},
{0x81, 0x66},
{0x82, 0x44},
{0x85, 0x04},
{0xcd, 0xf4},
{0x90, 0x33},
{0xa0, 0x44},
{0xbe, 0x00},
{0xc0, 0x08},
{0xc3, 0x10},
{0xc4, 0x08},
{0xc5, 0xf0},
{0xc6, 0xff},
{0xc7, 0x00},
{0xc8, 0x1a},
{0xc9, 0x80},
{0xe0, 0xf8},
{0xe6, 0x8b},
{0xd0, 0x40},
{0xf8, 0x20},
{0xfa, 0x0f},
{0x00, 0x00},
{0xbd, 0x01},
{0xb8, 0x00},
{0x29, 0x11},
};
static const struct m88ds3103_reg_val m88rs6000_dvbs2_init_reg_vals[] = {
{0x23, 0x07},
{0x08, 0x07},
{0x0c, 0x02},
{0x20, 0x00},
{0x21, 0x54},
{0x25, 0x82},
{0x27, 0x31},
{0x30, 0x08},
{0x32, 0x32},
{0x33, 0x35},
{0x35, 0xff},
{0x3a, 0x00},
{0x37, 0x10},
{0x38, 0x10},
{0x39, 0x02},
{0x42, 0x60},
{0x4a, 0x80},
{0x4b, 0x04},
{0x4d, 0x91},
{0x5d, 0xc8},
{0x50, 0x36},
{0x51, 0x36},
{0x52, 0x36},
{0x53, 0x36},
{0x63, 0x0f},
{0x64, 0x10},
{0x65, 0x20},
{0x68, 0x46},
{0x69, 0xcd},
{0x70, 0x20},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x40},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x60},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x80},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0xa0},
{0x71, 0x70},
{0x72, 0x04},
{0x73, 0x00},
{0x70, 0x1f},
{0x76, 0x38},
{0x77, 0xa6},
{0x78, 0x0c},
{0x79, 0x80},
{0x7f, 0x14},
{0x85, 0x08},
{0xcd, 0xf4},
{0x90, 0x33},
{0x86, 0x00},
{0x87, 0x0f},
{0x89, 0x00},
{0x8b, 0x44},
{0x8c, 0x66},
{0x9d, 0xc1},
{0x8a, 0x10},
{0xad, 0x40},
{0xa0, 0x44},
{0xbe, 0x00},
{0xc0, 0x08},
{0xc1, 0x10},
{0xc2, 0x08},
{0xc3, 0x10},
{0xc4, 0x08},
{0xc5, 0xf0},
{0xc6, 0xff},
{0xc7, 0x00},
{0xc8, 0x1a},
{0xc9, 0x80},
{0xca, 0x23},
{0xcb, 0x24},
{0xcc, 0xf4},
{0xce, 0x74},
{0x00, 0x00},
{0xbd, 0x01},
{0xb8, 0x00},
{0x29, 0x01},
};
#endif

View file

@ -0,0 +1,38 @@
/*
* Panasonic MN88472 DVB-T/T2/C demodulator driver
*
* Copyright (C) 2013 Antti Palosaari <crope@iki.fi>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef MN88472_H
#define MN88472_H
#include <linux/dvb/frontend.h>
struct mn88472_config {
/*
* Max num of bytes given I2C adapter could write at once.
* Default: none
*/
u16 i2c_wr_max;
/* Everything after that is returned by the driver. */
/*
* DVB frontend.
*/
struct dvb_frontend **fe;
};
#endif

View file

@ -0,0 +1,38 @@
/*
* Panasonic MN88473 DVB-T/T2/C demodulator driver
*
* Copyright (C) 2014 Antti Palosaari <crope@iki.fi>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef MN88473_H
#define MN88473_H
#include <linux/dvb/frontend.h>
struct mn88473_config {
/*
* Max num of bytes given I2C adapter could write at once.
* Default: none
*/
u16 i2c_wr_max;
/* Everything after that is returned by the driver. */
/*
* DVB frontend.
*/
struct dvb_frontend **fe;
};
#endif

View file

@ -258,13 +258,11 @@ static int rtl2832_rd_regs(struct rtl2832_priv *priv, u8 reg, u8 page, u8 *val,
return rtl2832_rd(priv, reg, val, len);
}
#if 0 /* currently not used */
/* write single register */
static int rtl2832_wr_reg(struct rtl2832_priv *priv, u8 reg, u8 page, u8 val)
{
return rtl2832_wr_regs(priv, reg, page, &val, 1);
}
#endif
/* read single register */
static int rtl2832_rd_reg(struct rtl2832_priv *priv, u8 reg, u8 page, u8 *val)
@ -599,6 +597,11 @@ static int rtl2832_set_frontend(struct dvb_frontend *fe)
if (fe->ops.tuner_ops.set_params)
fe->ops.tuner_ops.set_params(fe);
/* PIP mode related */
ret = rtl2832_wr_regs(priv, 0x92, 1, "\x00\x0f\xff", 3);
if (ret)
goto err;
/* If the frontend has get_if_frequency(), use it */
if (fe->ops.tuner_ops.get_if_frequency) {
u32 if_freq;
@ -661,7 +664,6 @@ static int rtl2832_set_frontend(struct dvb_frontend *fe)
if (ret)
goto err;
/* soft reset */
ret = rtl2832_wr_demod_reg(priv, DVBT_SOFT_RST, 0x1);
if (ret)
@ -1020,6 +1022,58 @@ static int rtl2832_deselect(struct i2c_adapter *adap, void *mux_priv,
return 0;
}
int rtl2832_enable_external_ts_if(struct dvb_frontend *fe)
{
struct rtl2832_priv *priv = fe->demodulator_priv;
int ret;
dev_dbg(&priv->i2c->dev, "%s: setting PIP mode\n", __func__);
ret = rtl2832_wr_regs(priv, 0x0c, 1, "\x5f\xff", 2);
if (ret)
goto err;
ret = rtl2832_wr_demod_reg(priv, DVBT_PIP_ON, 0x1);
if (ret)
goto err;
ret = rtl2832_wr_reg(priv, 0xbc, 0, 0x18);
if (ret)
goto err;
ret = rtl2832_wr_reg(priv, 0x22, 0, 0x01);
if (ret)
goto err;
ret = rtl2832_wr_reg(priv, 0x26, 0, 0x1f);
if (ret)
goto err;
ret = rtl2832_wr_reg(priv, 0x27, 0, 0xff);
if (ret)
goto err;
ret = rtl2832_wr_regs(priv, 0x92, 1, "\x7f\xf7\xff", 3);
if (ret)
goto err;
/* soft reset */
ret = rtl2832_wr_demod_reg(priv, DVBT_SOFT_RST, 0x1);
if (ret)
goto err;
ret = rtl2832_wr_demod_reg(priv, DVBT_SOFT_RST, 0x0);
if (ret)
goto err;
return 0;
err:
dev_dbg(&priv->i2c->dev, "%s: failed=%d\n", __func__, ret);
return ret;
}
EXPORT_SYMBOL(rtl2832_enable_external_ts_if);
struct i2c_adapter *rtl2832_get_i2c_adapter(struct dvb_frontend *fe)
{
struct rtl2832_priv *priv = fe->demodulator_priv;

View file

@ -64,6 +64,10 @@ extern struct i2c_adapter *rtl2832_get_private_i2c_adapter(
struct dvb_frontend *fe
);
extern int rtl2832_enable_external_ts_if(
struct dvb_frontend *fe
);
#else
static inline struct dvb_frontend *rtl2832_attach(
@ -89,6 +93,13 @@ static inline struct i2c_adapter *rtl2832_get_private_i2c_adapter(
return NULL;
}
static inline int rtl2832_enable_external_ts_if(
struct dvb_frontend *fe
)
{
return -ENODEV;
}
#endif

View file

@ -1013,6 +1013,10 @@ static int rtl2832_sdr_start_streaming(struct vb2_queue *vq, unsigned int count)
if (s->d->props->power_ctrl)
s->d->props->power_ctrl(s->d, 1);
/* enable ADC */
if (s->d->props->frontend_ctrl)
s->d->props->frontend_ctrl(s->fe, 1);
set_bit(POWER_ON, &s->flags);
ret = rtl2832_sdr_set_tuner(s);
@ -1064,6 +1068,10 @@ static void rtl2832_sdr_stop_streaming(struct vb2_queue *vq)
clear_bit(POWER_ON, &s->flags);
/* disable ADC */
if (s->d->props->frontend_ctrl)
s->d->props->frontend_ctrl(s->fe, 0);
if (s->d->props->power_ctrl)
s->d->props->power_ctrl(s->d, 0);

View file

@ -308,14 +308,16 @@ static int si2168_set_frontend(struct dvb_frontend *fe)
if (ret)
goto err;
memcpy(cmd.args, "\x14\x00\x09\x10\xe3\x18", 6);
memcpy(cmd.args, "\x14\x00\x09\x10\xe3\x08", 6);
cmd.args[5] |= s->ts_clock_inv ? 0x00 : 0x10;
cmd.wlen = 6;
cmd.rlen = 4;
ret = si2168_cmd_execute(s, &cmd);
if (ret)
goto err;
memcpy(cmd.args, "\x14\x00\x08\x10\xd7\x15", 6);
memcpy(cmd.args, "\x14\x00\x08\x10\xd7\x05", 6);
cmd.args[5] |= s->ts_clock_inv ? 0x00 : 0x10;
cmd.wlen = 6;
cmd.rlen = 4;
ret = si2168_cmd_execute(s, &cmd);
@ -453,27 +455,45 @@ static int si2168_init(struct dvb_frontend *fe)
dev_err(&s->client->dev,
"firmware file '%s' not found\n",
fw_file);
goto err;
goto error_fw_release;
}
}
dev_info(&s->client->dev, "downloading firmware from file '%s'\n",
fw_file);
for (remaining = fw->size; remaining > 0; remaining -= i2c_wr_max) {
len = remaining;
if (len > i2c_wr_max)
len = i2c_wr_max;
if ((fw->size % 17 == 0) && (fw->data[0] > 5)) {
/* firmware is in the new format */
for (remaining = fw->size; remaining > 0; remaining -= 17) {
len = fw->data[fw->size - remaining];
memcpy(cmd.args, &fw->data[(fw->size - remaining) + 1], len);
cmd.wlen = len;
cmd.rlen = 1;
ret = si2168_cmd_execute(s, &cmd);
if (ret) {
dev_err(&s->client->dev,
"firmware download failed=%d\n",
ret);
goto error_fw_release;
}
}
} else {
/* firmware is in the old format */
for (remaining = fw->size; remaining > 0; remaining -= i2c_wr_max) {
len = remaining;
if (len > i2c_wr_max)
len = i2c_wr_max;
memcpy(cmd.args, &fw->data[fw->size - remaining], len);
cmd.wlen = len;
cmd.rlen = 1;
ret = si2168_cmd_execute(s, &cmd);
if (ret) {
dev_err(&s->client->dev,
"firmware download failed=%d\n",
ret);
goto err;
memcpy(cmd.args, &fw->data[fw->size - remaining], len);
cmd.wlen = len;
cmd.rlen = 1;
ret = si2168_cmd_execute(s, &cmd);
if (ret) {
dev_err(&s->client->dev,
"firmware download failed=%d\n",
ret);
goto error_fw_release;
}
}
}
@ -487,6 +507,17 @@ static int si2168_init(struct dvb_frontend *fe)
if (ret)
goto err;
/* query firmware version */
memcpy(cmd.args, "\x11", 1);
cmd.wlen = 1;
cmd.rlen = 10;
ret = si2168_cmd_execute(s, &cmd);
if (ret)
goto err;
dev_dbg(&s->client->dev, "firmware version: %c.%c.%d\n",
cmd.args[6], cmd.args[7], cmd.args[8]);
/* set ts mode */
memcpy(cmd.args, "\x14\x00\x01\x10\x10\x00", 6);
cmd.args[4] |= s->ts_mode;
@ -498,17 +529,16 @@ static int si2168_init(struct dvb_frontend *fe)
s->fw_loaded = true;
warm:
dev_info(&s->client->dev, "found a '%s' in warm state\n",
si2168_ops.info.name);
warm:
s->active = true;
return 0;
err:
if (fw)
release_firmware(fw);
error_fw_release:
release_firmware(fw);
err:
dev_dbg(&s->client->dev, "failed=%d\n", ret);
return ret;
}
@ -670,6 +700,7 @@ static int si2168_probe(struct i2c_client *client,
*config->i2c_adapter = s->adapter;
*config->fe = &s->fe;
s->ts_mode = config->ts_mode;
s->ts_clock_inv = config->ts_clock_inv;
s->fw_loaded = false;
i2c_set_clientdata(client, s);

View file

@ -37,6 +37,10 @@ struct si2168_config {
/* TS mode */
u8 ts_mode;
/* TS clock inverted */
bool ts_clock_inv;
};
#define SI2168_TS_PARALLEL 0x06

View file

@ -38,6 +38,7 @@ struct si2168 {
bool active;
bool fw_loaded;
u8 ts_mode;
bool ts_clock_inv;
};
/* firmare command struct */

View file

@ -92,6 +92,9 @@ static int sp2_write_i2c(struct sp2 *s, u8 reg, u8 *buf, int len)
return -EIO;
}
dev_dbg(&s->client->dev, "addr=0x%04x, reg = 0x%02x, data = %*ph\n",
client->addr, reg, len, buf);
return 0;
}
@ -103,9 +106,6 @@ static int sp2_ci_op_cam(struct dvb_ca_en50221 *en50221, int slot, u8 acs,
int mem, ret;
int (*ci_op_cam)(void*, u8, int, u8, int*) = s->ci_control;
dev_dbg(&s->client->dev, "slot=%d, acs=0x%02x, addr=0x%04x, data = 0x%02x",
slot, acs, addr, data);
if (slot != 0)
return -EINVAL;
@ -140,13 +140,16 @@ static int sp2_ci_op_cam(struct dvb_ca_en50221 *en50221, int slot, u8 acs,
if (ret)
return ret;
if (read) {
dev_dbg(&s->client->dev, "cam read, addr=0x%04x, data = 0x%04x",
addr, mem);
dev_dbg(&s->client->dev, "%s: slot=%d, addr=0x%04x, %s, data=%x",
(read) ? "read" : "write", slot, addr,
(acs == SP2_CI_ATTR_ACS) ? "attr" : "io",
(read) ? mem : data);
if (read)
return mem;
} else {
else
return 0;
}
}
int sp2_ci_read_attribute_mem(struct dvb_ca_en50221 *en50221,
@ -407,7 +410,7 @@ err:
static int sp2_remove(struct i2c_client *client)
{
struct si2157 *s = i2c_get_clientdata(client);
struct sp2 *s = i2c_get_clientdata(client);
dev_dbg(&client->dev, "\n");

View file

@ -705,7 +705,7 @@ static int stb0899_send_diseqc_msg(struct dvb_frontend *fe, struct dvb_diseqc_ma
struct stb0899_state *state = fe->demodulator_priv;
u8 reg, i;
if (cmd->msg_len > 8)
if (cmd->msg_len > sizeof(cmd->msg))
return -EINVAL;
/* enable FIFO precharge */

View file

@ -2146,7 +2146,7 @@ static int stv090x_get_coldlock(struct stv090x_state *state, s32 timeout_dmd)
u32 reg;
s32 car_step, steps, cur_step, dir, freq, timeout_lock;
int lock = 0;
int lock;
if (state->srate >= 10000000)
timeout_lock = timeout_dmd / 3;
@ -2154,98 +2154,96 @@ static int stv090x_get_coldlock(struct stv090x_state *state, s32 timeout_dmd)
timeout_lock = timeout_dmd / 2;
lock = stv090x_get_dmdlock(state, timeout_lock); /* cold start wait */
if (!lock) {
if (state->srate >= 10000000) {
if (stv090x_chk_tmg(state)) {
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x1f) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x15) < 0)
goto err;
lock = stv090x_get_dmdlock(state, timeout_dmd);
} else {
lock = 0;
}
} else {
if (state->srate <= 4000000)
car_step = 1000;
else if (state->srate <= 7000000)
car_step = 2000;
else if (state->srate <= 10000000)
car_step = 3000;
else
car_step = 5000;
if (lock)
return lock;
steps = (state->search_range / 1000) / car_step;
steps /= 2;
steps = 2 * (steps + 1);
if (steps < 0)
steps = 2;
else if (steps > 12)
steps = 12;
cur_step = 1;
dir = 1;
if (!lock) {
freq = state->frequency;
state->tuner_bw = stv090x_car_width(state->srate, state->rolloff) + state->srate;
while ((cur_step <= steps) && (!lock)) {
if (dir > 0)
freq += cur_step * car_step;
else
freq -= cur_step * car_step;
/* Setup tuner */
if (stv090x_i2c_gate_ctrl(state, 1) < 0)
goto err;
if (state->config->tuner_set_frequency) {
if (state->config->tuner_set_frequency(fe, freq) < 0)
goto err_gateoff;
}
if (state->config->tuner_set_bandwidth) {
if (state->config->tuner_set_bandwidth(fe, state->tuner_bw) < 0)
goto err_gateoff;
}
if (stv090x_i2c_gate_ctrl(state, 0) < 0)
goto err;
msleep(50);
if (stv090x_i2c_gate_ctrl(state, 1) < 0)
goto err;
if (state->config->tuner_get_status) {
if (state->config->tuner_get_status(fe, &reg) < 0)
goto err_gateoff;
}
if (reg)
dprintk(FE_DEBUG, 1, "Tuner phase locked");
else
dprintk(FE_DEBUG, 1, "Tuner unlocked");
if (stv090x_i2c_gate_ctrl(state, 0) < 0)
goto err;
STV090x_WRITE_DEMOD(state, DMDISTATE, 0x1c);
if (STV090x_WRITE_DEMOD(state, CFRINIT1, 0x00) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, CFRINIT0, 0x00) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x1f) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x15) < 0)
goto err;
lock = stv090x_get_dmdlock(state, (timeout_dmd / 3));
dir *= -1;
cur_step++;
}
}
if (state->srate >= 10000000) {
if (stv090x_chk_tmg(state)) {
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x1f) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x15) < 0)
goto err;
return stv090x_get_dmdlock(state, timeout_dmd);
}
return 0;
}
if (state->srate <= 4000000)
car_step = 1000;
else if (state->srate <= 7000000)
car_step = 2000;
else if (state->srate <= 10000000)
car_step = 3000;
else
car_step = 5000;
steps = (state->search_range / 1000) / car_step;
steps /= 2;
steps = 2 * (steps + 1);
if (steps < 0)
steps = 2;
else if (steps > 12)
steps = 12;
cur_step = 1;
dir = 1;
freq = state->frequency;
state->tuner_bw = stv090x_car_width(state->srate, state->rolloff) + state->srate;
while ((cur_step <= steps) && (!lock)) {
if (dir > 0)
freq += cur_step * car_step;
else
freq -= cur_step * car_step;
/* Setup tuner */
if (stv090x_i2c_gate_ctrl(state, 1) < 0)
goto err;
if (state->config->tuner_set_frequency) {
if (state->config->tuner_set_frequency(fe, freq) < 0)
goto err_gateoff;
}
if (state->config->tuner_set_bandwidth) {
if (state->config->tuner_set_bandwidth(fe, state->tuner_bw) < 0)
goto err_gateoff;
}
if (stv090x_i2c_gate_ctrl(state, 0) < 0)
goto err;
msleep(50);
if (stv090x_i2c_gate_ctrl(state, 1) < 0)
goto err;
if (state->config->tuner_get_status) {
if (state->config->tuner_get_status(fe, &reg) < 0)
goto err_gateoff;
}
if (reg)
dprintk(FE_DEBUG, 1, "Tuner phase locked");
else
dprintk(FE_DEBUG, 1, "Tuner unlocked");
if (stv090x_i2c_gate_ctrl(state, 0) < 0)
goto err;
STV090x_WRITE_DEMOD(state, DMDISTATE, 0x1c);
if (STV090x_WRITE_DEMOD(state, CFRINIT1, 0x00) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, CFRINIT0, 0x00) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x1f) < 0)
goto err;
if (STV090x_WRITE_DEMOD(state, DMDISTATE, 0x15) < 0)
goto err;
lock = stv090x_get_dmdlock(state, (timeout_dmd / 3));
dir *= -1;
cur_step++;
}
return lock;
@ -2663,13 +2661,9 @@ static enum stv090x_signal_state stv090x_get_sig_params(struct stv090x_state *st
return STV090x_RANGEOK;
else if (abs(offst_freq) <= (stv090x_car_width(state->srate, state->rolloff) / 2000))
return STV090x_RANGEOK;
else
return STV090x_OUTOFRANGE; /* Out of Range */
} else {
if (abs(offst_freq) <= ((state->search_range / 2000) + 500))
return STV090x_RANGEOK;
else
return STV090x_OUTOFRANGE;
}
return STV090x_OUTOFRANGE;
@ -2789,6 +2783,12 @@ static u8 stv090x_optimize_carloop(struct stv090x_state *state, enum stv090x_mod
aclc = car_loop[i].crl_pilots_off_30;
}
} else { /* 16APSK and 32APSK */
/*
* This should never happen in practice, except if
* something is really wrong at the car_loop table.
*/
if (i >= 11)
i = 10;
if (state->srate <= 3000000)
aclc = car_loop_apsk_low[i].crl_pilots_on_2;
else if (state->srate <= 7000000)
@ -3470,7 +3470,20 @@ static enum dvbfe_search stv090x_search(struct dvb_frontend *fe)
if (props->frequency == 0)
return DVBFE_ALGO_SEARCH_INVALID;
state->delsys = props->delivery_system;
switch (props->delivery_system) {
case SYS_DSS:
state->delsys = STV090x_DSS;
break;
case SYS_DVBS:
state->delsys = STV090x_DVBS1;
break;
case SYS_DVBS2:
state->delsys = STV090x_DVBS2;
break;
default:
return DVBFE_ALGO_SEARCH_INVALID;
}
state->frequency = props->frequency;
state->srate = props->symbol_rate;
state->search_mode = STV090x_SEARCH_AUTO;
@ -4859,8 +4872,8 @@ err:
return -1;
}
int stv090x_set_gpio(struct dvb_frontend *fe, u8 gpio, u8 dir, u8 value,
u8 xor_value)
static int stv090x_set_gpio(struct dvb_frontend *fe, u8 gpio, u8 dir,
u8 value, u8 xor_value)
{
struct stv090x_state *state = fe->demodulator_priv;
u8 reg = 0;
@ -4871,7 +4884,6 @@ int stv090x_set_gpio(struct dvb_frontend *fe, u8 gpio, u8 dir, u8 value,
return stv090x_write_reg(state, STV090x_GPIOxCFG(gpio), reg);
}
EXPORT_SYMBOL(stv090x_set_gpio);
static struct dvb_frontend_ops stv090x_ops = {
.delsys = { SYS_DVBS, SYS_DVBS2, SYS_DSS },
@ -4908,7 +4920,7 @@ static struct dvb_frontend_ops stv090x_ops = {
};
struct dvb_frontend *stv090x_attach(const struct stv090x_config *config,
struct dvb_frontend *stv090x_attach(struct stv090x_config *config,
struct i2c_adapter *i2c,
enum stv090x_demodulator demod)
{
@ -4969,6 +4981,8 @@ struct dvb_frontend *stv090x_attach(const struct stv090x_config *config,
if (config->diseqc_envelope_mode)
stv090x_send_diseqc_burst(&state->frontend, SEC_MINI_A);
config->set_gpio = stv090x_set_gpio;
dprintk(FE_ERROR, 1, "Attaching %s demodulator(%d) Cut=0x%02x",
state->device == STV0900 ? "STV0900" : "STV0903",
demod,

View file

@ -89,29 +89,29 @@ struct stv090x_config {
bool diseqc_envelope_mode;
int (*tuner_init) (struct dvb_frontend *fe);
int (*tuner_sleep) (struct dvb_frontend *fe);
int (*tuner_set_mode) (struct dvb_frontend *fe, enum tuner_mode mode);
int (*tuner_set_frequency) (struct dvb_frontend *fe, u32 frequency);
int (*tuner_get_frequency) (struct dvb_frontend *fe, u32 *frequency);
int (*tuner_set_bandwidth) (struct dvb_frontend *fe, u32 bandwidth);
int (*tuner_get_bandwidth) (struct dvb_frontend *fe, u32 *bandwidth);
int (*tuner_set_bbgain) (struct dvb_frontend *fe, u32 gain);
int (*tuner_get_bbgain) (struct dvb_frontend *fe, u32 *gain);
int (*tuner_set_refclk) (struct dvb_frontend *fe, u32 refclk);
int (*tuner_get_status) (struct dvb_frontend *fe, u32 *status);
void (*tuner_i2c_lock) (struct dvb_frontend *fe, int lock);
int (*tuner_init)(struct dvb_frontend *fe);
int (*tuner_sleep)(struct dvb_frontend *fe);
int (*tuner_set_mode)(struct dvb_frontend *fe, enum tuner_mode mode);
int (*tuner_set_frequency)(struct dvb_frontend *fe, u32 frequency);
int (*tuner_get_frequency)(struct dvb_frontend *fe, u32 *frequency);
int (*tuner_set_bandwidth)(struct dvb_frontend *fe, u32 bandwidth);
int (*tuner_get_bandwidth)(struct dvb_frontend *fe, u32 *bandwidth);
int (*tuner_set_bbgain)(struct dvb_frontend *fe, u32 gain);
int (*tuner_get_bbgain)(struct dvb_frontend *fe, u32 *gain);
int (*tuner_set_refclk)(struct dvb_frontend *fe, u32 refclk);
int (*tuner_get_status)(struct dvb_frontend *fe, u32 *status);
void (*tuner_i2c_lock)(struct dvb_frontend *fe, int lock);
/* dir = 0 -> output, dir = 1 -> input/open-drain */
int (*set_gpio)(struct dvb_frontend *fe, u8 gpio, u8 dir, u8 value,
u8 xor_value);
};
#if IS_ENABLED(CONFIG_DVB_STV090x)
extern struct dvb_frontend *stv090x_attach(const struct stv090x_config *config,
struct i2c_adapter *i2c,
enum stv090x_demodulator demod);
/* dir = 0 -> output, dir = 1 -> input/open-drain */
extern int stv090x_set_gpio(struct dvb_frontend *fe, u8 gpio,
u8 dir, u8 value, u8 xor_value);
struct dvb_frontend *stv090x_attach(struct stv090x_config *config,
struct i2c_adapter *i2c,
enum stv090x_demodulator demod);
#else
@ -123,12 +123,6 @@ static inline struct dvb_frontend *stv090x_attach(const struct stv090x_config *c
return NULL;
}
static inline int stv090x_set_gpio(struct dvb_frontend *fe, u8 gpio,
u8 opd, u8 value, u8 xor_value)
{
printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
return -ENODEV;
}
#endif /* CONFIG_DVB_STV090x */
#endif /* __STV090x_H */

View file

@ -253,6 +253,5 @@ int fdtv_ca_register(struct firedtv *fdtv)
void fdtv_ca_release(struct firedtv *fdtv)
{
if (fdtv->cadev)
dvb_unregister_device(fdtv->cadev);
dvb_unregister_device(fdtv->cadev);
}

View file

@ -96,7 +96,7 @@ struct firedtv {
enum model_type type;
char subunit;
char isochannel;
s8 isochannel;
struct fdtv_ir_context *ir_context;
fe_sec_voltage_t voltage;

View file

@ -63,9 +63,9 @@ static inline struct adv7170 *to_adv7170(struct v4l2_subdev *sd)
static char *inputs[] = { "pass_through", "play_back" };
static enum v4l2_mbus_pixelcode adv7170_codes[] = {
V4L2_MBUS_FMT_UYVY8_2X8,
V4L2_MBUS_FMT_UYVY8_1X16,
static u32 adv7170_codes[] = {
MEDIA_BUS_FMT_UYVY8_2X8,
MEDIA_BUS_FMT_UYVY8_1X16,
};
/* ----------------------------------------------------------------------- */
@ -263,7 +263,7 @@ static int adv7170_s_routing(struct v4l2_subdev *sd,
}
static int adv7170_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(adv7170_codes))
return -EINVAL;
@ -278,9 +278,9 @@ static int adv7170_g_fmt(struct v4l2_subdev *sd,
u8 val = adv7170_read(sd, 0x7);
if ((val & 0x40) == (1 << 6))
mf->code = V4L2_MBUS_FMT_UYVY8_1X16;
mf->code = MEDIA_BUS_FMT_UYVY8_1X16;
else
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
mf->colorspace = V4L2_COLORSPACE_SMPTE170M;
mf->width = 0;
@ -297,11 +297,11 @@ static int adv7170_s_fmt(struct v4l2_subdev *sd,
int ret;
switch (mf->code) {
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
val &= ~0x40;
break;
case V4L2_MBUS_FMT_UYVY8_1X16:
case MEDIA_BUS_FMT_UYVY8_1X16:
val |= 0x40;
break;

View file

@ -60,9 +60,9 @@ static inline struct adv7175 *to_adv7175(struct v4l2_subdev *sd)
static char *inputs[] = { "pass_through", "play_back", "color_bar" };
static enum v4l2_mbus_pixelcode adv7175_codes[] = {
V4L2_MBUS_FMT_UYVY8_2X8,
V4L2_MBUS_FMT_UYVY8_1X16,
static u32 adv7175_codes[] = {
MEDIA_BUS_FMT_UYVY8_2X8,
MEDIA_BUS_FMT_UYVY8_1X16,
};
/* ----------------------------------------------------------------------- */
@ -301,7 +301,7 @@ static int adv7175_s_routing(struct v4l2_subdev *sd,
}
static int adv7175_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(adv7175_codes))
return -EINVAL;
@ -316,9 +316,9 @@ static int adv7175_g_fmt(struct v4l2_subdev *sd,
u8 val = adv7175_read(sd, 0x7);
if ((val & 0x40) == (1 << 6))
mf->code = V4L2_MBUS_FMT_UYVY8_1X16;
mf->code = MEDIA_BUS_FMT_UYVY8_1X16;
else
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
mf->colorspace = V4L2_COLORSPACE_SMPTE170M;
mf->width = 0;
@ -335,11 +335,11 @@ static int adv7175_s_fmt(struct v4l2_subdev *sd,
int ret;
switch (mf->code) {
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
val &= ~0x40;
break;
case V4L2_MBUS_FMT_UYVY8_1X16:
case MEDIA_BUS_FMT_UYVY8_1X16:
val |= 0x40;
break;

View file

@ -422,12 +422,12 @@ static void adv7180_exit_controls(struct adv7180_state *state)
}
static int adv7180_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index > 0)
return -EINVAL;
*code = V4L2_MBUS_FMT_YUYV8_2X8;
*code = MEDIA_BUS_FMT_YUYV8_2X8;
return 0;
}
@ -437,7 +437,7 @@ static int adv7180_mbus_fmt(struct v4l2_subdev *sd,
{
struct adv7180_state *state = to_state(sd);
fmt->code = V4L2_MBUS_FMT_YUYV8_2X8;
fmt->code = MEDIA_BUS_FMT_YUYV8_2X8;
fmt->colorspace = V4L2_COLORSPACE_SMPTE170M;
fmt->field = V4L2_FIELD_INTERLACED;
fmt->width = 720;

View file

@ -421,12 +421,12 @@ static int adv7183_g_input_status(struct v4l2_subdev *sd, u32 *status)
}
static int adv7183_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index > 0)
return -EINVAL;
*code = V4L2_MBUS_FMT_UYVY8_2X8;
*code = MEDIA_BUS_FMT_UYVY8_2X8;
return 0;
}
@ -435,7 +435,7 @@ static int adv7183_try_mbus_fmt(struct v4l2_subdev *sd,
{
struct adv7183 *decoder = to_adv7183(sd);
fmt->code = V4L2_MBUS_FMT_UYVY8_2X8;
fmt->code = MEDIA_BUS_FMT_UYVY8_2X8;
fmt->colorspace = V4L2_COLORSPACE_SMPTE170M;
if (decoder->std & V4L2_STD_525_60) {
fmt->field = V4L2_FIELD_SEQ_TB;

View file

@ -26,6 +26,7 @@
#include <linux/videodev2.h>
#include <linux/gpio.h>
#include <linux/workqueue.h>
#include <linux/hdmi.h>
#include <linux/v4l2-dv-timings.h>
#include <media/v4l2-device.h>
#include <media/v4l2-common.h>
@ -96,6 +97,10 @@ struct adv7511_state {
bool have_monitor;
/* timings from s_dv_timings */
struct v4l2_dv_timings dv_timings;
u32 fmt_code;
u32 colorspace;
u32 ycbcr_enc;
u32 quantization;
/* controls */
struct v4l2_ctrl *hdmi_mode_ctrl;
struct v4l2_ctrl *hotplug_ctrl;
@ -779,26 +784,234 @@ static int adv7511_get_edid(struct v4l2_subdev *sd, struct v4l2_edid *edid)
{
struct adv7511_state *state = get_adv7511_state(sd);
memset(edid->reserved, 0, sizeof(edid->reserved));
if (edid->pad != 0)
return -EINVAL;
if ((edid->blocks == 0) || (edid->blocks > 256))
return -EINVAL;
if (!state->edid.segments) {
v4l2_dbg(1, debug, sd, "EDID segment 0 not found\n");
return -ENODATA;
if (edid->start_block == 0 && edid->blocks == 0) {
edid->blocks = state->edid.segments * 2;
return 0;
}
if (state->edid.segments == 0)
return -ENODATA;
if (edid->start_block >= state->edid.segments * 2)
return -E2BIG;
if ((edid->blocks + edid->start_block) >= state->edid.segments * 2)
return -EINVAL;
if (edid->start_block + edid->blocks > state->edid.segments * 2)
edid->blocks = state->edid.segments * 2 - edid->start_block;
memcpy(edid->edid, &state->edid.data[edid->start_block * 128],
128 * edid->blocks);
return 0;
}
static int adv7511_enum_mbus_code(struct v4l2_subdev *sd,
struct v4l2_subdev_fh *fh,
struct v4l2_subdev_mbus_code_enum *code)
{
if (code->pad != 0)
return -EINVAL;
switch (code->index) {
case 0:
code->code = MEDIA_BUS_FMT_RGB888_1X24;
break;
case 1:
code->code = MEDIA_BUS_FMT_YUYV8_1X16;
break;
case 2:
code->code = MEDIA_BUS_FMT_UYVY8_1X16;
break;
default:
return -EINVAL;
}
return 0;
}
static void adv7511_fill_format(struct adv7511_state *state,
struct v4l2_mbus_framefmt *format)
{
memset(format, 0, sizeof(*format));
format->width = state->dv_timings.bt.width;
format->height = state->dv_timings.bt.height;
format->field = V4L2_FIELD_NONE;
}
static int adv7511_get_fmt(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh,
struct v4l2_subdev_format *format)
{
struct adv7511_state *state = get_adv7511_state(sd);
if (format->pad != 0)
return -EINVAL;
adv7511_fill_format(state, &format->format);
if (format->which == V4L2_SUBDEV_FORMAT_TRY) {
struct v4l2_mbus_framefmt *fmt;
fmt = v4l2_subdev_get_try_format(fh, format->pad);
format->format.code = fmt->code;
format->format.colorspace = fmt->colorspace;
format->format.ycbcr_enc = fmt->ycbcr_enc;
format->format.quantization = fmt->quantization;
} else {
format->format.code = state->fmt_code;
format->format.colorspace = state->colorspace;
format->format.ycbcr_enc = state->ycbcr_enc;
format->format.quantization = state->quantization;
}
return 0;
}
static int adv7511_set_fmt(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh,
struct v4l2_subdev_format *format)
{
struct adv7511_state *state = get_adv7511_state(sd);
/*
* Bitfield namings come the CEA-861-F standard, table 8 "Auxiliary
* Video Information (AVI) InfoFrame Format"
*
* c = Colorimetry
* ec = Extended Colorimetry
* y = RGB or YCbCr
* q = RGB Quantization Range
* yq = YCC Quantization Range
*/
u8 c = HDMI_COLORIMETRY_NONE;
u8 ec = HDMI_EXTENDED_COLORIMETRY_XV_YCC_601;
u8 y = HDMI_COLORSPACE_RGB;
u8 q = HDMI_QUANTIZATION_RANGE_DEFAULT;
u8 yq = HDMI_YCC_QUANTIZATION_RANGE_LIMITED;
if (format->pad != 0)
return -EINVAL;
switch (format->format.code) {
case MEDIA_BUS_FMT_UYVY8_1X16:
case MEDIA_BUS_FMT_YUYV8_1X16:
case MEDIA_BUS_FMT_RGB888_1X24:
break;
default:
return -EINVAL;
}
adv7511_fill_format(state, &format->format);
if (format->which == V4L2_SUBDEV_FORMAT_TRY) {
struct v4l2_mbus_framefmt *fmt;
fmt = v4l2_subdev_get_try_format(fh, format->pad);
fmt->code = format->format.code;
fmt->colorspace = format->format.colorspace;
fmt->ycbcr_enc = format->format.ycbcr_enc;
fmt->quantization = format->format.quantization;
return 0;
}
switch (format->format.code) {
case MEDIA_BUS_FMT_UYVY8_1X16:
adv7511_wr_and_or(sd, 0x15, 0xf0, 0x01);
adv7511_wr_and_or(sd, 0x16, 0x03, 0xb8);
y = HDMI_COLORSPACE_YUV422;
break;
case MEDIA_BUS_FMT_YUYV8_1X16:
adv7511_wr_and_or(sd, 0x15, 0xf0, 0x01);
adv7511_wr_and_or(sd, 0x16, 0x03, 0xbc);
y = HDMI_COLORSPACE_YUV422;
break;
case MEDIA_BUS_FMT_RGB888_1X24:
default:
adv7511_wr_and_or(sd, 0x15, 0xf0, 0x00);
adv7511_wr_and_or(sd, 0x16, 0x03, 0x00);
break;
}
state->fmt_code = format->format.code;
state->colorspace = format->format.colorspace;
state->ycbcr_enc = format->format.ycbcr_enc;
state->quantization = format->format.quantization;
switch (format->format.colorspace) {
case V4L2_COLORSPACE_ADOBERGB:
c = HDMI_COLORIMETRY_EXTENDED;
ec = y ? HDMI_EXTENDED_COLORIMETRY_ADOBE_YCC_601 :
HDMI_EXTENDED_COLORIMETRY_ADOBE_RGB;
break;
case V4L2_COLORSPACE_SMPTE170M:
c = y ? HDMI_COLORIMETRY_ITU_601 : HDMI_COLORIMETRY_NONE;
if (y && format->format.ycbcr_enc == V4L2_YCBCR_ENC_XV601) {
c = HDMI_COLORIMETRY_EXTENDED;
ec = HDMI_EXTENDED_COLORIMETRY_XV_YCC_601;
}
break;
case V4L2_COLORSPACE_REC709:
c = y ? HDMI_COLORIMETRY_ITU_709 : HDMI_COLORIMETRY_NONE;
if (y && format->format.ycbcr_enc == V4L2_YCBCR_ENC_XV709) {
c = HDMI_COLORIMETRY_EXTENDED;
ec = HDMI_EXTENDED_COLORIMETRY_XV_YCC_709;
}
break;
case V4L2_COLORSPACE_SRGB:
c = y ? HDMI_COLORIMETRY_EXTENDED : HDMI_COLORIMETRY_NONE;
ec = y ? HDMI_EXTENDED_COLORIMETRY_S_YCC_601 :
HDMI_EXTENDED_COLORIMETRY_XV_YCC_601;
break;
case V4L2_COLORSPACE_BT2020:
c = HDMI_COLORIMETRY_EXTENDED;
if (y && format->format.ycbcr_enc == V4L2_YCBCR_ENC_BT2020_CONST_LUM)
ec = 5; /* Not yet available in hdmi.h */
else
ec = 6; /* Not yet available in hdmi.h */
break;
default:
break;
}
/*
* CEA-861-F says that for RGB formats the YCC range must match the
* RGB range, although sources should ignore the YCC range.
*
* The RGB quantization range shouldn't be non-zero if the EDID doesn't
* have the Q bit set in the Video Capabilities Data Block, however this
* isn't checked at the moment. The assumption is that the application
* knows the EDID and can detect this.
*
* The same is true for the YCC quantization range: non-standard YCC
* quantization ranges should only be sent if the EDID has the YQ bit
* set in the Video Capabilities Data Block.
*/
switch (format->format.quantization) {
case V4L2_QUANTIZATION_FULL_RANGE:
q = y ? HDMI_QUANTIZATION_RANGE_DEFAULT :
HDMI_QUANTIZATION_RANGE_FULL;
yq = q ? q - 1 : HDMI_YCC_QUANTIZATION_RANGE_FULL;
break;
case V4L2_QUANTIZATION_LIM_RANGE:
q = y ? HDMI_QUANTIZATION_RANGE_DEFAULT :
HDMI_QUANTIZATION_RANGE_LIMITED;
yq = q ? q - 1 : HDMI_YCC_QUANTIZATION_RANGE_LIMITED;
break;
}
adv7511_wr_and_or(sd, 0x4a, 0xbf, 0);
adv7511_wr_and_or(sd, 0x55, 0x9f, y << 5);
adv7511_wr_and_or(sd, 0x56, 0x3f, c << 6);
adv7511_wr_and_or(sd, 0x57, 0x83, (ec << 4) | (q << 2));
adv7511_wr_and_or(sd, 0x59, 0x0f, yq << 4);
adv7511_wr_and_or(sd, 0x4a, 0xff, 1);
return 0;
}
static const struct v4l2_subdev_pad_ops adv7511_pad_ops = {
.get_edid = adv7511_get_edid,
.enum_mbus_code = adv7511_enum_mbus_code,
.get_fmt = adv7511_get_fmt,
.set_fmt = adv7511_set_fmt,
.enum_dv_timings = adv7511_enum_dv_timings,
.dv_timings_cap = adv7511_dv_timings_cap,
};
@ -1116,6 +1329,8 @@ static int adv7511_probe(struct i2c_client *client, const struct i2c_device_id *
return -ENODEV;
}
memcpy(&state->pdata, pdata, sizeof(state->pdata));
state->fmt_code = MEDIA_BUS_FMT_RGB888_1X24;
state->colorspace = V4L2_COLORSPACE_SRGB;
sd = &state->sd;

View file

@ -88,7 +88,7 @@ struct adv7604_reg_seq {
};
struct adv7604_format_info {
enum v4l2_mbus_pixelcode code;
u32 code;
u8 op_ch_sel;
bool rgb_out;
bool swap_cb_cr;
@ -749,77 +749,77 @@ static void adv7604_write_reg_seq(struct v4l2_subdev *sd,
*/
static const struct adv7604_format_info adv7604_formats[] = {
{ V4L2_MBUS_FMT_RGB888_1X24, ADV7604_OP_CH_SEL_RGB, true, false,
{ MEDIA_BUS_FMT_RGB888_1X24, ADV7604_OP_CH_SEL_RGB, true, false,
ADV7604_OP_MODE_SEL_SDR_444 | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YUYV8_2X8, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV8_2X8, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YVYU8_2X8, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU8_2X8, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YUYV10_2X10, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV10_2X10, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_10BIT },
{ V4L2_MBUS_FMT_YVYU10_2X10, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU10_2X10, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_10BIT },
{ V4L2_MBUS_FMT_YUYV12_2X12, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV12_2X12, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_YVYU12_2X12, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU12_2X12, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_UYVY8_1X16, ADV7604_OP_CH_SEL_RBG, false, false,
{ MEDIA_BUS_FMT_UYVY8_1X16, ADV7604_OP_CH_SEL_RBG, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_VYUY8_1X16, ADV7604_OP_CH_SEL_RBG, false, true,
{ MEDIA_BUS_FMT_VYUY8_1X16, ADV7604_OP_CH_SEL_RBG, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YUYV8_1X16, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV8_1X16, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YVYU8_1X16, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU8_1X16, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_UYVY10_1X20, ADV7604_OP_CH_SEL_RBG, false, false,
{ MEDIA_BUS_FMT_UYVY10_1X20, ADV7604_OP_CH_SEL_RBG, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_10BIT },
{ V4L2_MBUS_FMT_VYUY10_1X20, ADV7604_OP_CH_SEL_RBG, false, true,
{ MEDIA_BUS_FMT_VYUY10_1X20, ADV7604_OP_CH_SEL_RBG, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_10BIT },
{ V4L2_MBUS_FMT_YUYV10_1X20, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV10_1X20, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_10BIT },
{ V4L2_MBUS_FMT_YVYU10_1X20, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU10_1X20, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_10BIT },
{ V4L2_MBUS_FMT_UYVY12_1X24, ADV7604_OP_CH_SEL_RBG, false, false,
{ MEDIA_BUS_FMT_UYVY12_1X24, ADV7604_OP_CH_SEL_RBG, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_VYUY12_1X24, ADV7604_OP_CH_SEL_RBG, false, true,
{ MEDIA_BUS_FMT_VYUY12_1X24, ADV7604_OP_CH_SEL_RBG, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_YUYV12_1X24, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV12_1X24, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_YVYU12_1X24, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU12_1X24, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
};
static const struct adv7604_format_info adv7611_formats[] = {
{ V4L2_MBUS_FMT_RGB888_1X24, ADV7604_OP_CH_SEL_RGB, true, false,
{ MEDIA_BUS_FMT_RGB888_1X24, ADV7604_OP_CH_SEL_RGB, true, false,
ADV7604_OP_MODE_SEL_SDR_444 | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YUYV8_2X8, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV8_2X8, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YVYU8_2X8, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU8_2X8, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YUYV12_2X12, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV12_2X12, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_YVYU12_2X12, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU12_2X12, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422 | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_UYVY8_1X16, ADV7604_OP_CH_SEL_RBG, false, false,
{ MEDIA_BUS_FMT_UYVY8_1X16, ADV7604_OP_CH_SEL_RBG, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_VYUY8_1X16, ADV7604_OP_CH_SEL_RBG, false, true,
{ MEDIA_BUS_FMT_VYUY8_1X16, ADV7604_OP_CH_SEL_RBG, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YUYV8_1X16, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV8_1X16, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_YVYU8_1X16, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU8_1X16, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_8BIT },
{ V4L2_MBUS_FMT_UYVY12_1X24, ADV7604_OP_CH_SEL_RBG, false, false,
{ MEDIA_BUS_FMT_UYVY12_1X24, ADV7604_OP_CH_SEL_RBG, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_VYUY12_1X24, ADV7604_OP_CH_SEL_RBG, false, true,
{ MEDIA_BUS_FMT_VYUY12_1X24, ADV7604_OP_CH_SEL_RBG, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_YUYV12_1X24, ADV7604_OP_CH_SEL_RGB, false, false,
{ MEDIA_BUS_FMT_YUYV12_1X24, ADV7604_OP_CH_SEL_RGB, false, false,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
{ V4L2_MBUS_FMT_YVYU12_1X24, ADV7604_OP_CH_SEL_RGB, false, true,
{ MEDIA_BUS_FMT_YVYU12_1X24, ADV7604_OP_CH_SEL_RGB, false, true,
ADV7604_OP_MODE_SEL_SDR_422_2X | ADV7604_OP_FORMAT_SEL_12BIT },
};
static const struct adv7604_format_info *
adv7604_format_info(struct adv7604_state *state, enum v4l2_mbus_pixelcode code)
adv7604_format_info(struct adv7604_state *state, u32 code)
{
unsigned int i;
@ -1917,7 +1917,7 @@ static int adv7604_set_format(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh,
info = adv7604_format_info(state, format->format.code);
if (info == NULL)
info = adv7604_format_info(state, V4L2_MBUS_FMT_YUYV8_2X8);
info = adv7604_format_info(state, MEDIA_BUS_FMT_YUYV8_2X8);
adv7604_fill_format(state, &format->format);
format->format.code = info->code;
@ -1997,19 +1997,7 @@ static int adv7604_get_edid(struct v4l2_subdev *sd, struct v4l2_edid *edid)
struct adv7604_state *state = to_state(sd);
u8 *data = NULL;
if (edid->pad > ADV7604_PAD_HDMI_PORT_D)
return -EINVAL;
if (edid->blocks == 0)
return -EINVAL;
if (edid->blocks > 2)
return -EINVAL;
if (edid->start_block > 1)
return -EINVAL;
if (edid->start_block == 1)
edid->blocks = 1;
if (edid->blocks > state->edid.blocks)
edid->blocks = state->edid.blocks;
memset(edid->reserved, 0, sizeof(edid->reserved));
switch (edid->pad) {
case ADV7604_PAD_HDMI_PORT_A:
@ -2021,14 +2009,24 @@ static int adv7604_get_edid(struct v4l2_subdev *sd, struct v4l2_edid *edid)
break;
default:
return -EINVAL;
break;
}
if (!data)
if (edid->start_block == 0 && edid->blocks == 0) {
edid->blocks = data ? state->edid.blocks : 0;
return 0;
}
if (data == NULL)
return -ENODATA;
memcpy(edid->edid,
data + edid->start_block * 128,
edid->blocks * 128);
if (edid->start_block >= state->edid.blocks)
return -EINVAL;
if (edid->start_block + edid->blocks > state->edid.blocks)
edid->blocks = state->edid.blocks - edid->start_block;
memcpy(edid->edid, data + edid->start_block * 128, edid->blocks * 128);
return 0;
}
@ -2068,6 +2066,8 @@ static int adv7604_set_edid(struct v4l2_subdev *sd, struct v4l2_edid *edid)
int err;
int i;
memset(edid->reserved, 0, sizeof(edid->reserved));
if (edid->pad > ADV7604_PAD_HDMI_PORT_D)
return -EINVAL;
if (edid->start_block != 0)
@ -2164,7 +2164,6 @@ static int adv7604_set_edid(struct v4l2_subdev *sd, struct v4l2_edid *edid)
return -EIO;
}
/* enable hotplug after 100 ms */
queue_delayed_work(state->work_queues,
&state->delayed_work_enable_hotplug, HZ / 10);
@ -2807,7 +2806,7 @@ static int adv7604_probe(struct i2c_client *client,
}
state->timings = cea640x480;
state->format = adv7604_format_info(state, V4L2_MBUS_FMT_YUYV8_2X8);
state->format = adv7604_format_info(state, MEDIA_BUS_FMT_YUYV8_2X8);
sd = &state->sd;
v4l2_i2c_subdev_init(sd, client, &adv7604_ops);

View file

@ -1877,12 +1877,12 @@ static int adv7842_s_routing(struct v4l2_subdev *sd,
}
static int adv7842_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index)
return -EINVAL;
/* Good enough for now */
*code = V4L2_MBUS_FMT_FIXED;
*code = MEDIA_BUS_FMT_FIXED;
return 0;
}
@ -1893,7 +1893,7 @@ static int adv7842_g_mbus_fmt(struct v4l2_subdev *sd,
fmt->width = state->timings.bt.width;
fmt->height = state->timings.bt.height;
fmt->code = V4L2_MBUS_FMT_FIXED;
fmt->code = MEDIA_BUS_FMT_FIXED;
fmt->field = V4L2_FIELD_NONE;
if (state->mode == ADV7842_MODE_SDP) {
@ -2028,16 +2028,7 @@ static int adv7842_get_edid(struct v4l2_subdev *sd, struct v4l2_edid *edid)
struct adv7842_state *state = to_state(sd);
u8 *data = NULL;
if (edid->pad > ADV7842_EDID_PORT_VGA)
return -EINVAL;
if (edid->blocks == 0)
return -EINVAL;
if (edid->blocks > 2)
return -EINVAL;
if (edid->start_block > 1)
return -EINVAL;
if (edid->start_block == 1)
edid->blocks = 1;
memset(edid->reserved, 0, sizeof(edid->reserved));
switch (edid->pad) {
case ADV7842_EDID_PORT_A:
@ -2052,12 +2043,23 @@ static int adv7842_get_edid(struct v4l2_subdev *sd, struct v4l2_edid *edid)
default:
return -EINVAL;
}
if (edid->start_block == 0 && edid->blocks == 0) {
edid->blocks = data ? 2 : 0;
return 0;
}
if (!data)
return -ENODATA;
memcpy(edid->edid,
data + edid->start_block * 128,
edid->blocks * 128);
if (edid->start_block >= 2)
return -EINVAL;
if (edid->start_block + edid->blocks > 2)
edid->blocks = 2 - edid->start_block;
memcpy(edid->edid, data + edid->start_block * 128, edid->blocks * 128);
return 0;
}
@ -2066,12 +2068,16 @@ static int adv7842_set_edid(struct v4l2_subdev *sd, struct v4l2_edid *e)
struct adv7842_state *state = to_state(sd);
int err = 0;
memset(e->reserved, 0, sizeof(e->reserved));
if (e->pad > ADV7842_EDID_PORT_VGA)
return -EINVAL;
if (e->start_block != 0)
return -EINVAL;
if (e->blocks > 2)
if (e->blocks > 2) {
e->blocks = 2;
return -E2BIG;
}
/* todo, per edid */
state->aspect_ratio = v4l2_calc_aspect_ratio(e->edid[0x15],

View file

@ -102,7 +102,7 @@ static int ak881x_try_g_mbus_fmt(struct v4l2_subdev *sd,
v4l_bound_align_image(&mf->width, 0, 720, 2,
&mf->height, 0, ak881x->lines, 1, 0);
mf->field = V4L2_FIELD_INTERLACED;
mf->code = V4L2_MBUS_FMT_YUYV8_2X8;
mf->code = MEDIA_BUS_FMT_YUYV8_2X8;
mf->colorspace = V4L2_COLORSPACE_SMPTE170M;
return 0;
@ -112,19 +112,19 @@ static int ak881x_s_mbus_fmt(struct v4l2_subdev *sd,
struct v4l2_mbus_framefmt *mf)
{
if (mf->field != V4L2_FIELD_INTERLACED ||
mf->code != V4L2_MBUS_FMT_YUYV8_2X8)
mf->code != MEDIA_BUS_FMT_YUYV8_2X8)
return -EINVAL;
return ak881x_try_g_mbus_fmt(sd, mf);
}
static int ak881x_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index)
return -EINVAL;
*code = V4L2_MBUS_FMT_YUYV8_2X8;
*code = MEDIA_BUS_FMT_YUYV8_2X8;
return 0;
}

View file

@ -879,7 +879,7 @@ void cx25840_std_setup(struct i2c_client *client)
/* Sets horizontal blanking delay and active lines */
cx25840_write(client, 0x470, hblank);
cx25840_write(client, 0x471,
0xff & (((hblank >> 8) & 0x3) | (hactive << 4)));
(((hblank >> 8) & 0x3) | (hactive << 4)) & 0xff);
cx25840_write(client, 0x472, hactive >> 4);
/* Sets burst gate delay */
@ -888,13 +888,13 @@ void cx25840_std_setup(struct i2c_client *client)
/* Sets vertical blanking delay and active duration */
cx25840_write(client, 0x474, vblank);
cx25840_write(client, 0x475,
0xff & (((vblank >> 8) & 0x3) | (vactive << 4)));
(((vblank >> 8) & 0x3) | (vactive << 4)) & 0xff);
cx25840_write(client, 0x476, vactive >> 4);
cx25840_write(client, 0x477, vblank656);
/* Sets src decimation rate */
cx25840_write(client, 0x478, 0xff & src_decimation);
cx25840_write(client, 0x479, 0xff & (src_decimation >> 8));
cx25840_write(client, 0x478, src_decimation & 0xff);
cx25840_write(client, 0x479, (src_decimation >> 8) & 0xff);
/* Sets Luma and UV Low pass filters */
cx25840_write(client, 0x47a, luma_lpf << 6 | ((uv_lpf << 4) & 0x30));
@ -904,8 +904,8 @@ void cx25840_std_setup(struct i2c_client *client)
/* Sets SC Step*/
cx25840_write(client, 0x47c, sc);
cx25840_write(client, 0x47d, 0xff & sc >> 8);
cx25840_write(client, 0x47e, 0xff & sc >> 16);
cx25840_write(client, 0x47d, (sc >> 8) & 0xff);
cx25840_write(client, 0x47e, (sc >> 16) & 0xff);
/* Sets VBI parameters */
if (std & V4L2_STD_625_50) {
@ -1373,7 +1373,7 @@ static int cx25840_s_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt
int HSC, VSC, Vsrc, Hsrc, filter, Vlines;
int is_50Hz = !(state->std & V4L2_STD_525_60);
if (fmt->code != V4L2_MBUS_FMT_FIXED)
if (fmt->code != MEDIA_BUS_FMT_FIXED)
return -EINVAL;
fmt->field = V4L2_FIELD_INTERLACED;

View file

@ -113,7 +113,7 @@ int cx25840_loadfw(struct i2c_client *client)
const u8 *ptr;
const char *fwname = get_fw_name(client);
int size, retval;
int MAX_BUF_SIZE = FWSEND;
int max_buf_size = FWSEND;
u32 gpio_oe = 0, gpio_da = 0;
if (is_cx2388x(state)) {
@ -122,10 +122,9 @@ int cx25840_loadfw(struct i2c_client *client)
gpio_da = cx25840_read(client, 0x164);
}
if (is_cx231xx(state) && MAX_BUF_SIZE > 16) {
v4l_err(client, " Firmware download size changed to 16 bytes max length\n");
MAX_BUF_SIZE = 16; /* cx231xx cannot accept more than 16 bytes at a time */
}
/* cx231xx cannot accept more than 16 bytes at a time */
if (is_cx231xx(state) && max_buf_size > 16)
max_buf_size = 16;
if (request_firmware(&fw, fwname, FWDEV(client)) != 0) {
v4l_err(client, "unable to open firmware %s\n", fwname);
@ -140,7 +139,7 @@ int cx25840_loadfw(struct i2c_client *client)
size = fw->size;
ptr = fw->data;
while (size > 0) {
int len = min(MAX_BUF_SIZE - 2, size);
int len = min(max_buf_size - 2, size);
memcpy(buffer + 2, ptr, len);

View file

@ -464,8 +464,7 @@ static int ir_remove(struct i2c_client *client)
cancel_delayed_work_sync(&ir->work);
/* unregister device */
if (ir->rc)
rc_unregister_device(ir->rc);
rc_unregister_device(ir->rc);
/* free memory */
return 0;

View file

@ -57,14 +57,14 @@ static struct v4l2_mbus_framefmt m5mols_default_ffmt[M5MOLS_RESTYPE_MAX] = {
[M5MOLS_RESTYPE_MONITOR] = {
.width = 1920,
.height = 1080,
.code = V4L2_MBUS_FMT_VYUY8_2X8,
.code = MEDIA_BUS_FMT_VYUY8_2X8,
.field = V4L2_FIELD_NONE,
.colorspace = V4L2_COLORSPACE_JPEG,
},
[M5MOLS_RESTYPE_CAPTURE] = {
.width = 1920,
.height = 1080,
.code = V4L2_MBUS_FMT_JPEG_1X8,
.code = MEDIA_BUS_FMT_JPEG_1X8,
.field = V4L2_FIELD_NONE,
.colorspace = V4L2_COLORSPACE_JPEG,
},
@ -479,7 +479,7 @@ static int m5mols_get_version(struct v4l2_subdev *sd)
* __find_restype - Lookup M-5MOLS resolution type according to pixel code
* @code: pixel code
*/
static enum m5mols_restype __find_restype(enum v4l2_mbus_pixelcode code)
static enum m5mols_restype __find_restype(u32 code)
{
enum m5mols_restype type = M5MOLS_RESTYPE_MONITOR;

View file

@ -192,12 +192,12 @@ static int ml86v7667_g_input_status(struct v4l2_subdev *sd, u32 *status)
}
static int ml86v7667_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index > 0)
return -EINVAL;
*code = V4L2_MBUS_FMT_YUYV8_2X8;
*code = MEDIA_BUS_FMT_YUYV8_2X8;
return 0;
}
@ -207,7 +207,7 @@ static int ml86v7667_mbus_fmt(struct v4l2_subdev *sd,
{
struct ml86v7667_priv *priv = to_ml86v7667(sd);
fmt->code = V4L2_MBUS_FMT_YUYV8_2X8;
fmt->code = MEDIA_BUS_FMT_YUYV8_2X8;
fmt->colorspace = V4L2_COLORSPACE_SMPTE170M;
/* The top field is always transferred first by the chip */
fmt->field = V4L2_FIELD_INTERLACED_TB;

View file

@ -323,7 +323,7 @@ static int mt9m032_enum_mbus_code(struct v4l2_subdev *subdev,
if (code->index != 0)
return -EINVAL;
code->code = V4L2_MBUS_FMT_Y8_1X8;
code->code = MEDIA_BUS_FMT_Y8_1X8;
return 0;
}
@ -331,7 +331,7 @@ static int mt9m032_enum_frame_size(struct v4l2_subdev *subdev,
struct v4l2_subdev_fh *fh,
struct v4l2_subdev_frame_size_enum *fse)
{
if (fse->index != 0 || fse->code != V4L2_MBUS_FMT_Y8_1X8)
if (fse->index != 0 || fse->code != MEDIA_BUS_FMT_Y8_1X8)
return -EINVAL;
fse->min_width = MT9M032_COLUMN_SIZE_DEF;
@ -759,7 +759,7 @@ static int mt9m032_probe(struct i2c_client *client,
sensor->format.width = sensor->crop.width;
sensor->format.height = sensor->crop.height;
sensor->format.code = V4L2_MBUS_FMT_Y8_1X8;
sensor->format.code = MEDIA_BUS_FMT_Y8_1X8;
sensor->format.field = V4L2_FIELD_NONE;
sensor->format.colorspace = V4L2_COLORSPACE_SRGB;

View file

@ -950,9 +950,9 @@ static int mt9p031_open(struct v4l2_subdev *subdev, struct v4l2_subdev_fh *fh)
format = v4l2_subdev_get_try_format(fh, 0);
if (mt9p031->model == MT9P031_MODEL_MONOCHROME)
format->code = V4L2_MBUS_FMT_Y12_1X12;
format->code = MEDIA_BUS_FMT_Y12_1X12;
else
format->code = V4L2_MBUS_FMT_SGRBG12_1X12;
format->code = MEDIA_BUS_FMT_SGRBG12_1X12;
format->width = MT9P031_WINDOW_WIDTH_DEF;
format->height = MT9P031_WINDOW_HEIGHT_DEF;
@ -1120,9 +1120,9 @@ static int mt9p031_probe(struct i2c_client *client,
mt9p031->crop.top = MT9P031_ROW_START_DEF;
if (mt9p031->model == MT9P031_MODEL_MONOCHROME)
mt9p031->format.code = V4L2_MBUS_FMT_Y12_1X12;
mt9p031->format.code = MEDIA_BUS_FMT_Y12_1X12;
else
mt9p031->format.code = V4L2_MBUS_FMT_SGRBG12_1X12;
mt9p031->format.code = MEDIA_BUS_FMT_SGRBG12_1X12;
mt9p031->format.width = MT9P031_WINDOW_WIDTH_DEF;
mt9p031->format.height = MT9P031_WINDOW_HEIGHT_DEF;

View file

@ -333,7 +333,7 @@ static int mt9t001_enum_mbus_code(struct v4l2_subdev *subdev,
if (code->index > 0)
return -EINVAL;
code->code = V4L2_MBUS_FMT_SGRBG10_1X10;
code->code = MEDIA_BUS_FMT_SGRBG10_1X10;
return 0;
}
@ -341,7 +341,7 @@ static int mt9t001_enum_frame_size(struct v4l2_subdev *subdev,
struct v4l2_subdev_fh *fh,
struct v4l2_subdev_frame_size_enum *fse)
{
if (fse->index >= 8 || fse->code != V4L2_MBUS_FMT_SGRBG10_1X10)
if (fse->index >= 8 || fse->code != MEDIA_BUS_FMT_SGRBG10_1X10)
return -EINVAL;
fse->min_width = (MT9T001_WINDOW_WIDTH_DEF + 1) / fse->index;
@ -792,7 +792,7 @@ static int mt9t001_open(struct v4l2_subdev *subdev, struct v4l2_subdev_fh *fh)
crop->height = MT9T001_WINDOW_HEIGHT_DEF + 1;
format = v4l2_subdev_get_try_format(fh, 0);
format->code = V4L2_MBUS_FMT_SGRBG10_1X10;
format->code = MEDIA_BUS_FMT_SGRBG10_1X10;
format->width = MT9T001_WINDOW_WIDTH_DEF + 1;
format->height = MT9T001_WINDOW_HEIGHT_DEF + 1;
format->field = V4L2_FIELD_NONE;
@ -917,7 +917,7 @@ static int mt9t001_probe(struct i2c_client *client,
mt9t001->crop.width = MT9T001_WINDOW_WIDTH_DEF + 1;
mt9t001->crop.height = MT9T001_WINDOW_HEIGHT_DEF + 1;
mt9t001->format.code = V4L2_MBUS_FMT_SGRBG10_1X10;
mt9t001->format.code = MEDIA_BUS_FMT_SGRBG10_1X10;
mt9t001->format.width = MT9T001_WINDOW_WIDTH_DEF + 1;
mt9t001->format.height = MT9T001_WINDOW_HEIGHT_DEF + 1;
mt9t001->format.field = V4L2_FIELD_NONE;

View file

@ -325,18 +325,18 @@ static int mt9v011_reset(struct v4l2_subdev *sd, u32 val)
}
static int mt9v011_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index > 0)
return -EINVAL;
*code = V4L2_MBUS_FMT_SGRBG8_1X8;
*code = MEDIA_BUS_FMT_SGRBG8_1X8;
return 0;
}
static int mt9v011_try_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *fmt)
{
if (fmt->code != V4L2_MBUS_FMT_SGRBG8_1X8)
if (fmt->code != MEDIA_BUS_FMT_SGRBG8_1X8)
return -EINVAL;
v4l_bound_align_image(&fmt->width, 48, 639, 1,

View file

@ -454,7 +454,7 @@ static int mt9v032_enum_mbus_code(struct v4l2_subdev *subdev,
if (code->index > 0)
return -EINVAL;
code->code = V4L2_MBUS_FMT_SGRBG10_1X10;
code->code = MEDIA_BUS_FMT_SGRBG10_1X10;
return 0;
}
@ -462,7 +462,7 @@ static int mt9v032_enum_frame_size(struct v4l2_subdev *subdev,
struct v4l2_subdev_fh *fh,
struct v4l2_subdev_frame_size_enum *fse)
{
if (fse->index >= 3 || fse->code != V4L2_MBUS_FMT_SGRBG10_1X10)
if (fse->index >= 3 || fse->code != MEDIA_BUS_FMT_SGRBG10_1X10)
return -EINVAL;
fse->min_width = MT9V032_WINDOW_WIDTH_DEF / (1 << fse->index);
@ -814,9 +814,9 @@ static int mt9v032_open(struct v4l2_subdev *subdev, struct v4l2_subdev_fh *fh)
format = v4l2_subdev_get_try_format(fh, 0);
if (mt9v032->model->color)
format->code = V4L2_MBUS_FMT_SGRBG10_1X10;
format->code = MEDIA_BUS_FMT_SGRBG10_1X10;
else
format->code = V4L2_MBUS_FMT_Y10_1X10;
format->code = MEDIA_BUS_FMT_Y10_1X10;
format->width = MT9V032_WINDOW_WIDTH_DEF;
format->height = MT9V032_WINDOW_HEIGHT_DEF;
@ -966,9 +966,9 @@ static int mt9v032_probe(struct i2c_client *client,
mt9v032->crop.height = MT9V032_WINDOW_HEIGHT_DEF;
if (mt9v032->model->color)
mt9v032->format.code = V4L2_MBUS_FMT_SGRBG10_1X10;
mt9v032->format.code = MEDIA_BUS_FMT_SGRBG10_1X10;
else
mt9v032->format.code = V4L2_MBUS_FMT_Y10_1X10;
mt9v032->format.code = MEDIA_BUS_FMT_Y10_1X10;
mt9v032->format.width = MT9V032_WINDOW_WIDTH_DEF;
mt9v032->format.height = MT9V032_WINDOW_HEIGHT_DEF;

View file

@ -112,7 +112,7 @@ MODULE_PARM_DESC(debug, "Enable module debug trace. Set to 1 to enable.");
#define REG_TERM 0xFFFF
struct noon010_format {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
u16 ispctl1_reg;
};
@ -175,23 +175,23 @@ static const struct noon010_frmsize noon010_sizes[] = {
/* Supported pixel formats. */
static const struct noon010_format noon010_formats[] = {
{
.code = V4L2_MBUS_FMT_YUYV8_2X8,
.code = MEDIA_BUS_FMT_YUYV8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x03,
}, {
.code = V4L2_MBUS_FMT_YVYU8_2X8,
.code = MEDIA_BUS_FMT_YVYU8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x02,
}, {
.code = V4L2_MBUS_FMT_VYUY8_2X8,
.code = MEDIA_BUS_FMT_VYUY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0,
}, {
.code = V4L2_MBUS_FMT_UYVY8_2X8,
.code = MEDIA_BUS_FMT_UYVY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x01,
}, {
.code = V4L2_MBUS_FMT_RGB565_2X8_BE,
.code = MEDIA_BUS_FMT_RGB565_2X8_BE,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x40,
},

View file

@ -632,31 +632,31 @@ static int ov7670_detect(struct v4l2_subdev *sd)
* The magic matrix numbers come from OmniVision.
*/
static struct ov7670_format_struct {
enum v4l2_mbus_pixelcode mbus_code;
u32 mbus_code;
enum v4l2_colorspace colorspace;
struct regval_list *regs;
int cmatrix[CMATRIX_LEN];
} ov7670_formats[] = {
{
.mbus_code = V4L2_MBUS_FMT_YUYV8_2X8,
.mbus_code = MEDIA_BUS_FMT_YUYV8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.regs = ov7670_fmt_yuv422,
.cmatrix = { 128, -128, 0, -34, -94, 128 },
},
{
.mbus_code = V4L2_MBUS_FMT_RGB444_2X8_PADHI_LE,
.mbus_code = MEDIA_BUS_FMT_RGB444_2X8_PADHI_LE,
.colorspace = V4L2_COLORSPACE_SRGB,
.regs = ov7670_fmt_rgb444,
.cmatrix = { 179, -179, 0, -61, -176, 228 },
},
{
.mbus_code = V4L2_MBUS_FMT_RGB565_2X8_LE,
.mbus_code = MEDIA_BUS_FMT_RGB565_2X8_LE,
.colorspace = V4L2_COLORSPACE_SRGB,
.regs = ov7670_fmt_rgb565,
.cmatrix = { 179, -179, 0, -61, -176, 228 },
},
{
.mbus_code = V4L2_MBUS_FMT_SBGGR8_1X8,
.mbus_code = MEDIA_BUS_FMT_SBGGR8_1X8,
.colorspace = V4L2_COLORSPACE_SRGB,
.regs = ov7670_fmt_raw,
.cmatrix = { 0, 0, 0, 0, 0, 0 },
@ -772,7 +772,7 @@ static void ov7675_get_framerate(struct v4l2_subdev *sd,
pll_factor = PLL_FACTOR;
clkrc++;
if (info->fmt->mbus_code == V4L2_MBUS_FMT_SBGGR8_1X8)
if (info->fmt->mbus_code == MEDIA_BUS_FMT_SBGGR8_1X8)
clkrc = (clkrc >> 1);
tpf->numerator = 1;
@ -810,7 +810,7 @@ static int ov7675_set_framerate(struct v4l2_subdev *sd,
} else {
clkrc = (5 * pll_factor * info->clock_speed * tpf->numerator) /
(4 * tpf->denominator);
if (info->fmt->mbus_code == V4L2_MBUS_FMT_SBGGR8_1X8)
if (info->fmt->mbus_code == MEDIA_BUS_FMT_SBGGR8_1X8)
clkrc = (clkrc << 1);
clkrc--;
}
@ -900,7 +900,7 @@ static int ov7670_set_hw(struct v4l2_subdev *sd, int hstart, int hstop,
static int ov7670_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= N_OV7670_FMTS)
return -EINVAL;

View file

@ -384,17 +384,17 @@ static const struct ov965x_framesize ov965x_framesizes[] = {
};
struct ov965x_pixfmt {
enum v4l2_mbus_pixelcode code;
u32 code;
u32 colorspace;
/* REG_TSLB value, only bits [3:2] may be set. */
u8 tslb_reg;
};
static const struct ov965x_pixfmt ov965x_formats[] = {
{ V4L2_MBUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG, 0x00},
{ V4L2_MBUS_FMT_YVYU8_2X8, V4L2_COLORSPACE_JPEG, 0x04},
{ V4L2_MBUS_FMT_UYVY8_2X8, V4L2_COLORSPACE_JPEG, 0x0c},
{ V4L2_MBUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_JPEG, 0x08},
{ MEDIA_BUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG, 0x00},
{ MEDIA_BUS_FMT_YVYU8_2X8, V4L2_COLORSPACE_JPEG, 0x04},
{ MEDIA_BUS_FMT_UYVY8_2X8, V4L2_COLORSPACE_JPEG, 0x0c},
{ MEDIA_BUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_JPEG, 0x08},
};
/*

View file

@ -27,8 +27,8 @@
#define DRIVER_NAME "S5C73M3"
#define S5C73M3_ISP_FMT V4L2_MBUS_FMT_VYUY8_2X8
#define S5C73M3_JPEG_FMT V4L2_MBUS_FMT_S5C_UYVY_JPEG_1X8
#define S5C73M3_ISP_FMT MEDIA_BUS_FMT_VYUY8_2X8
#define S5C73M3_JPEG_FMT MEDIA_BUS_FMT_S5C_UYVY_JPEG_1X8
/* Subdevs pad index definitions */
enum s5c73m3_pads {
@ -402,7 +402,7 @@ struct s5c73m3 {
const struct s5c73m3_frame_size *sensor_pix_size[2];
const struct s5c73m3_frame_size *oif_pix_size[2];
enum v4l2_mbus_pixelcode mbus_code;
u32 mbus_code;
const struct s5c73m3_interval *fiv;

View file

@ -151,7 +151,7 @@ static const struct s5k4ecgx_frmsize s5k4ecgx_prev_sizes[] = {
#define S5K4ECGX_NUM_PREV ARRAY_SIZE(s5k4ecgx_prev_sizes)
struct s5k4ecgx_pixfmt {
enum v4l2_mbus_pixelcode code;
u32 code;
u32 colorspace;
/* REG_TC_PCFG_Format register value */
u16 reg_p_format;
@ -159,7 +159,7 @@ struct s5k4ecgx_pixfmt {
/* By default value, output from sensor will be YUV422 0-255 */
static const struct s5k4ecgx_pixfmt s5k4ecgx_formats[] = {
{ V4L2_MBUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG, 5 },
{ MEDIA_BUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG, 5 },
};
static const char * const s5k4ecgx_supply_names[] = {

View file

@ -248,7 +248,7 @@ enum s5k5baf_gpio_id {
#define NUM_ISP_PADS 2
struct s5k5baf_pixfmt {
enum v4l2_mbus_pixelcode code;
u32 code;
u32 colorspace;
/* REG_P_FMT(x) register value */
u16 reg_p_fmt;
@ -331,10 +331,10 @@ struct s5k5baf {
};
static const struct s5k5baf_pixfmt s5k5baf_formats[] = {
{ V4L2_MBUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_JPEG, 5 },
{ MEDIA_BUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_JPEG, 5 },
/* range 16-240 */
{ V4L2_MBUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_REC709, 6 },
{ V4L2_MBUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_JPEG, 0 },
{ MEDIA_BUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_REC709, 6 },
{ MEDIA_BUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_JPEG, 0 },
};
static struct v4l2_rect s5k5baf_cis_rect = {
@ -1206,7 +1206,7 @@ static int s5k5baf_enum_mbus_code(struct v4l2_subdev *sd,
if (code->pad == PAD_CIS) {
if (code->index > 0)
return -EINVAL;
code->code = V4L2_MBUS_FMT_FIXED;
code->code = MEDIA_BUS_FMT_FIXED;
return 0;
}
@ -1227,7 +1227,7 @@ static int s5k5baf_enum_frame_size(struct v4l2_subdev *sd,
return -EINVAL;
if (fse->pad == PAD_CIS) {
fse->code = V4L2_MBUS_FMT_FIXED;
fse->code = MEDIA_BUS_FMT_FIXED;
fse->min_width = S5K5BAF_CIS_WIDTH;
fse->max_width = S5K5BAF_CIS_WIDTH;
fse->min_height = S5K5BAF_CIS_HEIGHT;
@ -1252,7 +1252,7 @@ static void s5k5baf_try_cis_format(struct v4l2_mbus_framefmt *mf)
{
mf->width = S5K5BAF_CIS_WIDTH;
mf->height = S5K5BAF_CIS_HEIGHT;
mf->code = V4L2_MBUS_FMT_FIXED;
mf->code = MEDIA_BUS_FMT_FIXED;
mf->colorspace = V4L2_COLORSPACE_JPEG;
mf->field = V4L2_FIELD_NONE;
}

View file

@ -80,7 +80,7 @@ static inline struct s5k6a3 *sd_to_s5k6a3(struct v4l2_subdev *sd)
static const struct v4l2_mbus_framefmt s5k6a3_formats[] = {
{
.code = V4L2_MBUS_FMT_SGRBG10_1X10,
.code = MEDIA_BUS_FMT_SGRBG10_1X10,
.colorspace = V4L2_COLORSPACE_SRGB,
.field = V4L2_FIELD_NONE,
}

View file

@ -191,7 +191,7 @@ struct s5k6aa_regval {
};
struct s5k6aa_pixfmt {
enum v4l2_mbus_pixelcode code;
u32 code;
u32 colorspace;
/* REG_P_FMT(x) register value */
u16 reg_p_fmt;
@ -285,10 +285,10 @@ static struct s5k6aa_regval s5k6aa_analog_config[] = {
/* TODO: Add RGB888 and Bayer format */
static const struct s5k6aa_pixfmt s5k6aa_formats[] = {
{ V4L2_MBUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG, 5 },
{ MEDIA_BUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG, 5 },
/* range 16-240 */
{ V4L2_MBUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_REC709, 6 },
{ V4L2_MBUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_JPEG, 0 },
{ MEDIA_BUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_REC709, 6 },
{ MEDIA_BUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_JPEG, 0 },
};
static const struct s5k6aa_interval s5k6aa_intervals[] = {

View file

@ -562,7 +562,7 @@ static int saa6752hs_g_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefm
h->video_format = SAA6752HS_VF_D1;
f->width = v4l2_format_table[h->video_format].fmt.pix.width;
f->height = v4l2_format_table[h->video_format].fmt.pix.height;
f->code = V4L2_MBUS_FMT_FIXED;
f->code = MEDIA_BUS_FMT_FIXED;
f->field = V4L2_FIELD_INTERLACED;
f->colorspace = V4L2_COLORSPACE_SMPTE170M;
return 0;
@ -572,7 +572,7 @@ static int saa6752hs_try_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_frame
{
int dist_352, dist_480, dist_720;
f->code = V4L2_MBUS_FMT_FIXED;
f->code = MEDIA_BUS_FMT_FIXED;
dist_352 = abs(f->width - 352);
dist_480 = abs(f->width - 480);
@ -599,7 +599,7 @@ static int saa6752hs_s_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefm
{
struct saa6752hs_state *h = to_state(sd);
if (f->code != V4L2_MBUS_FMT_FIXED)
if (f->code != MEDIA_BUS_FMT_FIXED)
return -EINVAL;
/*

View file

@ -1172,7 +1172,7 @@ static int saa711x_s_sliced_fmt(struct v4l2_subdev *sd, struct v4l2_sliced_vbi_f
static int saa711x_s_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *fmt)
{
if (fmt->code != V4L2_MBUS_FMT_FIXED)
if (fmt->code != MEDIA_BUS_FMT_FIXED)
return -EINVAL;
fmt->field = V4L2_FIELD_INTERLACED;
fmt->colorspace = V4L2_COLORSPACE_SMPTE170M;

View file

@ -998,7 +998,7 @@ static int saa717x_s_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt
v4l2_dbg(1, debug, sd, "decoder set size\n");
if (fmt->code != V4L2_MBUS_FMT_FIXED)
if (fmt->code != MEDIA_BUS_FMT_FIXED)
return -EINVAL;
/* FIXME need better bounds checking here */

View file

@ -65,264 +65,36 @@ static int bounds_check(struct device *dev, uint32_t val,
static void print_pll(struct device *dev, struct smiapp_pll *pll)
{
dev_dbg(dev, "pre_pll_clk_div\t%d\n", pll->pre_pll_clk_div);
dev_dbg(dev, "pll_multiplier \t%d\n", pll->pll_multiplier);
if (pll->flags != SMIAPP_PLL_FLAG_NO_OP_CLOCKS) {
dev_dbg(dev, "op_sys_clk_div \t%d\n", pll->op_sys_clk_div);
dev_dbg(dev, "op_pix_clk_div \t%d\n", pll->op_pix_clk_div);
dev_dbg(dev, "pre_pll_clk_div\t%u\n", pll->pre_pll_clk_div);
dev_dbg(dev, "pll_multiplier \t%u\n", pll->pll_multiplier);
if (!(pll->flags & SMIAPP_PLL_FLAG_NO_OP_CLOCKS)) {
dev_dbg(dev, "op_sys_clk_div \t%u\n", pll->op.sys_clk_div);
dev_dbg(dev, "op_pix_clk_div \t%u\n", pll->op.pix_clk_div);
}
dev_dbg(dev, "vt_sys_clk_div \t%d\n", pll->vt_sys_clk_div);
dev_dbg(dev, "vt_pix_clk_div \t%d\n", pll->vt_pix_clk_div);
dev_dbg(dev, "vt_sys_clk_div \t%u\n", pll->vt.sys_clk_div);
dev_dbg(dev, "vt_pix_clk_div \t%u\n", pll->vt.pix_clk_div);
dev_dbg(dev, "ext_clk_freq_hz \t%d\n", pll->ext_clk_freq_hz);
dev_dbg(dev, "pll_ip_clk_freq_hz \t%d\n", pll->pll_ip_clk_freq_hz);
dev_dbg(dev, "pll_op_clk_freq_hz \t%d\n", pll->pll_op_clk_freq_hz);
if (pll->flags & SMIAPP_PLL_FLAG_NO_OP_CLOCKS) {
dev_dbg(dev, "op_sys_clk_freq_hz \t%d\n",
pll->op_sys_clk_freq_hz);
dev_dbg(dev, "op_pix_clk_freq_hz \t%d\n",
pll->op_pix_clk_freq_hz);
dev_dbg(dev, "ext_clk_freq_hz \t%u\n", pll->ext_clk_freq_hz);
dev_dbg(dev, "pll_ip_clk_freq_hz \t%u\n", pll->pll_ip_clk_freq_hz);
dev_dbg(dev, "pll_op_clk_freq_hz \t%u\n", pll->pll_op_clk_freq_hz);
if (!(pll->flags & SMIAPP_PLL_FLAG_NO_OP_CLOCKS)) {
dev_dbg(dev, "op_sys_clk_freq_hz \t%u\n",
pll->op.sys_clk_freq_hz);
dev_dbg(dev, "op_pix_clk_freq_hz \t%u\n",
pll->op.pix_clk_freq_hz);
}
dev_dbg(dev, "vt_sys_clk_freq_hz \t%d\n", pll->vt_sys_clk_freq_hz);
dev_dbg(dev, "vt_pix_clk_freq_hz \t%d\n", pll->vt_pix_clk_freq_hz);
dev_dbg(dev, "vt_sys_clk_freq_hz \t%u\n", pll->vt.sys_clk_freq_hz);
dev_dbg(dev, "vt_pix_clk_freq_hz \t%u\n", pll->vt.pix_clk_freq_hz);
}
/*
* Heuristically guess the PLL tree for a given common multiplier and
* divisor. Begin with the operational timing and continue to video
* timing once operational timing has been verified.
*
* @mul is the PLL multiplier and @div is the common divisor
* (pre_pll_clk_div and op_sys_clk_div combined). The final PLL
* multiplier will be a multiple of @mul.
*
* @return Zero on success, error code on error.
*/
static int __smiapp_pll_calculate(struct device *dev,
const struct smiapp_pll_limits *limits,
struct smiapp_pll *pll, uint32_t mul,
uint32_t div, uint32_t lane_op_clock_ratio)
static int check_all_bounds(struct device *dev,
const struct smiapp_pll_limits *limits,
const struct smiapp_pll_branch_limits *op_limits,
struct smiapp_pll *pll,
struct smiapp_pll_branch *op_pll)
{
uint32_t sys_div;
uint32_t best_pix_div = INT_MAX >> 1;
uint32_t vt_op_binning_div;
/*
* Higher multipliers (and divisors) are often required than
* necessitated by the external clock and the output clocks.
* There are limits for all values in the clock tree. These
* are the minimum and maximum multiplier for mul.
*/
uint32_t more_mul_min, more_mul_max;
uint32_t more_mul_factor;
uint32_t min_vt_div, max_vt_div, vt_div;
uint32_t min_sys_div, max_sys_div;
unsigned int i;
int rval;
/*
* Get pre_pll_clk_div so that our pll_op_clk_freq_hz won't be
* too high.
*/
dev_dbg(dev, "pre_pll_clk_div %d\n", pll->pre_pll_clk_div);
/* Don't go above max pll multiplier. */
more_mul_max = limits->max_pll_multiplier / mul;
dev_dbg(dev, "more_mul_max: max_pll_multiplier check: %d\n",
more_mul_max);
/* Don't go above max pll op frequency. */
more_mul_max =
min_t(uint32_t,
more_mul_max,
limits->max_pll_op_freq_hz
/ (pll->ext_clk_freq_hz / pll->pre_pll_clk_div * mul));
dev_dbg(dev, "more_mul_max: max_pll_op_freq_hz check: %d\n",
more_mul_max);
/* Don't go above the division capability of op sys clock divider. */
more_mul_max = min(more_mul_max,
limits->op.max_sys_clk_div * pll->pre_pll_clk_div
/ div);
dev_dbg(dev, "more_mul_max: max_op_sys_clk_div check: %d\n",
more_mul_max);
/* Ensure we won't go above min_pll_multiplier. */
more_mul_max = min(more_mul_max,
DIV_ROUND_UP(limits->max_pll_multiplier, mul));
dev_dbg(dev, "more_mul_max: min_pll_multiplier check: %d\n",
more_mul_max);
/* Ensure we won't go below min_pll_op_freq_hz. */
more_mul_min = DIV_ROUND_UP(limits->min_pll_op_freq_hz,
pll->ext_clk_freq_hz / pll->pre_pll_clk_div
* mul);
dev_dbg(dev, "more_mul_min: min_pll_op_freq_hz check: %d\n",
more_mul_min);
/* Ensure we won't go below min_pll_multiplier. */
more_mul_min = max(more_mul_min,
DIV_ROUND_UP(limits->min_pll_multiplier, mul));
dev_dbg(dev, "more_mul_min: min_pll_multiplier check: %d\n",
more_mul_min);
if (more_mul_min > more_mul_max) {
dev_dbg(dev,
"unable to compute more_mul_min and more_mul_max\n");
return -EINVAL;
}
more_mul_factor = lcm(div, pll->pre_pll_clk_div) / div;
dev_dbg(dev, "more_mul_factor: %d\n", more_mul_factor);
more_mul_factor = lcm(more_mul_factor, limits->op.min_sys_clk_div);
dev_dbg(dev, "more_mul_factor: min_op_sys_clk_div: %d\n",
more_mul_factor);
i = roundup(more_mul_min, more_mul_factor);
if (!is_one_or_even(i))
i <<= 1;
dev_dbg(dev, "final more_mul: %d\n", i);
if (i > more_mul_max) {
dev_dbg(dev, "final more_mul is bad, max %d\n", more_mul_max);
return -EINVAL;
}
pll->pll_multiplier = mul * i;
pll->op_sys_clk_div = div * i / pll->pre_pll_clk_div;
dev_dbg(dev, "op_sys_clk_div: %d\n", pll->op_sys_clk_div);
pll->pll_ip_clk_freq_hz = pll->ext_clk_freq_hz
/ pll->pre_pll_clk_div;
pll->pll_op_clk_freq_hz = pll->pll_ip_clk_freq_hz
* pll->pll_multiplier;
/* Derive pll_op_clk_freq_hz. */
pll->op_sys_clk_freq_hz =
pll->pll_op_clk_freq_hz / pll->op_sys_clk_div;
pll->op_pix_clk_div = pll->bits_per_pixel;
dev_dbg(dev, "op_pix_clk_div: %d\n", pll->op_pix_clk_div);
pll->op_pix_clk_freq_hz =
pll->op_sys_clk_freq_hz / pll->op_pix_clk_div;
/*
* Some sensors perform analogue binning and some do this
* digitally. The ones doing this digitally can be roughly be
* found out using this formula. The ones doing this digitally
* should run at higher clock rate, so smaller divisor is used
* on video timing side.
*/
if (limits->min_line_length_pck_bin > limits->min_line_length_pck
/ pll->binning_horizontal)
vt_op_binning_div = pll->binning_horizontal;
else
vt_op_binning_div = 1;
dev_dbg(dev, "vt_op_binning_div: %d\n", vt_op_binning_div);
/*
* Profile 2 supports vt_pix_clk_div E [4, 10]
*
* Horizontal binning can be used as a base for difference in
* divisors. One must make sure that horizontal blanking is
* enough to accommodate the CSI-2 sync codes.
*
* Take scaling factor into account as well.
*
* Find absolute limits for the factor of vt divider.
*/
dev_dbg(dev, "scale_m: %d\n", pll->scale_m);
min_vt_div = DIV_ROUND_UP(pll->op_pix_clk_div * pll->op_sys_clk_div
* pll->scale_n,
lane_op_clock_ratio * vt_op_binning_div
* pll->scale_m);
/* Find smallest and biggest allowed vt divisor. */
dev_dbg(dev, "min_vt_div: %d\n", min_vt_div);
min_vt_div = max(min_vt_div,
DIV_ROUND_UP(pll->pll_op_clk_freq_hz,
limits->vt.max_pix_clk_freq_hz));
dev_dbg(dev, "min_vt_div: max_vt_pix_clk_freq_hz: %d\n",
min_vt_div);
min_vt_div = max_t(uint32_t, min_vt_div,
limits->vt.min_pix_clk_div
* limits->vt.min_sys_clk_div);
dev_dbg(dev, "min_vt_div: min_vt_clk_div: %d\n", min_vt_div);
max_vt_div = limits->vt.max_sys_clk_div * limits->vt.max_pix_clk_div;
dev_dbg(dev, "max_vt_div: %d\n", max_vt_div);
max_vt_div = min(max_vt_div,
DIV_ROUND_UP(pll->pll_op_clk_freq_hz,
limits->vt.min_pix_clk_freq_hz));
dev_dbg(dev, "max_vt_div: min_vt_pix_clk_freq_hz: %d\n",
max_vt_div);
/*
* Find limitsits for sys_clk_div. Not all values are possible
* with all values of pix_clk_div.
*/
min_sys_div = limits->vt.min_sys_clk_div;
dev_dbg(dev, "min_sys_div: %d\n", min_sys_div);
min_sys_div = max(min_sys_div,
DIV_ROUND_UP(min_vt_div,
limits->vt.max_pix_clk_div));
dev_dbg(dev, "min_sys_div: max_vt_pix_clk_div: %d\n", min_sys_div);
min_sys_div = max(min_sys_div,
pll->pll_op_clk_freq_hz
/ limits->vt.max_sys_clk_freq_hz);
dev_dbg(dev, "min_sys_div: max_pll_op_clk_freq_hz: %d\n", min_sys_div);
min_sys_div = clk_div_even_up(min_sys_div);
dev_dbg(dev, "min_sys_div: one or even: %d\n", min_sys_div);
max_sys_div = limits->vt.max_sys_clk_div;
dev_dbg(dev, "max_sys_div: %d\n", max_sys_div);
max_sys_div = min(max_sys_div,
DIV_ROUND_UP(max_vt_div,
limits->vt.min_pix_clk_div));
dev_dbg(dev, "max_sys_div: min_vt_pix_clk_div: %d\n", max_sys_div);
max_sys_div = min(max_sys_div,
DIV_ROUND_UP(pll->pll_op_clk_freq_hz,
limits->vt.min_pix_clk_freq_hz));
dev_dbg(dev, "max_sys_div: min_vt_pix_clk_freq_hz: %d\n", max_sys_div);
/*
* Find pix_div such that a legal pix_div * sys_div results
* into a value which is not smaller than div, the desired
* divisor.
*/
for (vt_div = min_vt_div; vt_div <= max_vt_div;
vt_div += 2 - (vt_div & 1)) {
for (sys_div = min_sys_div;
sys_div <= max_sys_div;
sys_div += 2 - (sys_div & 1)) {
uint16_t pix_div = DIV_ROUND_UP(vt_div, sys_div);
if (pix_div < limits->vt.min_pix_clk_div
|| pix_div > limits->vt.max_pix_clk_div) {
dev_dbg(dev,
"pix_div %d too small or too big (%d--%d)\n",
pix_div,
limits->vt.min_pix_clk_div,
limits->vt.max_pix_clk_div);
continue;
}
/* Check if this one is better. */
if (pix_div * sys_div
<= roundup(min_vt_div, best_pix_div))
best_pix_div = pix_div;
}
if (best_pix_div < INT_MAX >> 1)
break;
}
pll->vt_sys_clk_div = DIV_ROUND_UP(min_vt_div, best_pix_div);
pll->vt_pix_clk_div = best_pix_div;
pll->vt_sys_clk_freq_hz =
pll->pll_op_clk_freq_hz / pll->vt_sys_clk_div;
pll->vt_pix_clk_freq_hz =
pll->vt_sys_clk_freq_hz / pll->vt_pix_clk_div;
pll->pixel_rate_csi =
pll->op_pix_clk_freq_hz * lane_op_clock_ratio;
rval = bounds_check(dev, pll->pll_ip_clk_freq_hz,
limits->min_pll_ip_freq_hz,
limits->max_pll_ip_freq_hz,
@ -339,35 +111,38 @@ static int __smiapp_pll_calculate(struct device *dev,
"pll_op_clk_freq_hz");
if (!rval)
rval = bounds_check(
dev, pll->op_sys_clk_div,
limits->op.min_sys_clk_div, limits->op.max_sys_clk_div,
dev, op_pll->sys_clk_div,
op_limits->min_sys_clk_div, op_limits->max_sys_clk_div,
"op_sys_clk_div");
if (!rval)
rval = bounds_check(
dev, pll->op_pix_clk_div,
limits->op.min_pix_clk_div, limits->op.max_pix_clk_div,
"op_pix_clk_div");
if (!rval)
rval = bounds_check(
dev, pll->op_sys_clk_freq_hz,
limits->op.min_sys_clk_freq_hz,
limits->op.max_sys_clk_freq_hz,
dev, op_pll->sys_clk_freq_hz,
op_limits->min_sys_clk_freq_hz,
op_limits->max_sys_clk_freq_hz,
"op_sys_clk_freq_hz");
if (!rval)
rval = bounds_check(
dev, pll->op_pix_clk_freq_hz,
limits->op.min_pix_clk_freq_hz,
limits->op.max_pix_clk_freq_hz,
dev, op_pll->pix_clk_freq_hz,
op_limits->min_pix_clk_freq_hz,
op_limits->max_pix_clk_freq_hz,
"op_pix_clk_freq_hz");
/*
* If there are no OP clocks, the VT clocks are contained in
* the OP clock struct.
*/
if (pll->flags & SMIAPP_PLL_FLAG_NO_OP_CLOCKS)
return rval;
if (!rval)
rval = bounds_check(
dev, pll->vt_sys_clk_freq_hz,
dev, pll->vt.sys_clk_freq_hz,
limits->vt.min_sys_clk_freq_hz,
limits->vt.max_sys_clk_freq_hz,
"vt_sys_clk_freq_hz");
if (!rval)
rval = bounds_check(
dev, pll->vt_pix_clk_freq_hz,
dev, pll->vt.pix_clk_freq_hz,
limits->vt.min_pix_clk_freq_hz,
limits->vt.max_pix_clk_freq_hz,
"vt_pix_clk_freq_hz");
@ -375,10 +150,258 @@ static int __smiapp_pll_calculate(struct device *dev,
return rval;
}
/*
* Heuristically guess the PLL tree for a given common multiplier and
* divisor. Begin with the operational timing and continue to video
* timing once operational timing has been verified.
*
* @mul is the PLL multiplier and @div is the common divisor
* (pre_pll_clk_div and op_sys_clk_div combined). The final PLL
* multiplier will be a multiple of @mul.
*
* @return Zero on success, error code on error.
*/
static int __smiapp_pll_calculate(
struct device *dev, const struct smiapp_pll_limits *limits,
const struct smiapp_pll_branch_limits *op_limits,
struct smiapp_pll *pll, struct smiapp_pll_branch *op_pll, uint32_t mul,
uint32_t div, uint32_t lane_op_clock_ratio)
{
uint32_t sys_div;
uint32_t best_pix_div = INT_MAX >> 1;
uint32_t vt_op_binning_div;
/*
* Higher multipliers (and divisors) are often required than
* necessitated by the external clock and the output clocks.
* There are limits for all values in the clock tree. These
* are the minimum and maximum multiplier for mul.
*/
uint32_t more_mul_min, more_mul_max;
uint32_t more_mul_factor;
uint32_t min_vt_div, max_vt_div, vt_div;
uint32_t min_sys_div, max_sys_div;
unsigned int i;
/*
* Get pre_pll_clk_div so that our pll_op_clk_freq_hz won't be
* too high.
*/
dev_dbg(dev, "pre_pll_clk_div %u\n", pll->pre_pll_clk_div);
/* Don't go above max pll multiplier. */
more_mul_max = limits->max_pll_multiplier / mul;
dev_dbg(dev, "more_mul_max: max_pll_multiplier check: %u\n",
more_mul_max);
/* Don't go above max pll op frequency. */
more_mul_max =
min_t(uint32_t,
more_mul_max,
limits->max_pll_op_freq_hz
/ (pll->ext_clk_freq_hz / pll->pre_pll_clk_div * mul));
dev_dbg(dev, "more_mul_max: max_pll_op_freq_hz check: %u\n",
more_mul_max);
/* Don't go above the division capability of op sys clock divider. */
more_mul_max = min(more_mul_max,
op_limits->max_sys_clk_div * pll->pre_pll_clk_div
/ div);
dev_dbg(dev, "more_mul_max: max_op_sys_clk_div check: %u\n",
more_mul_max);
/* Ensure we won't go above min_pll_multiplier. */
more_mul_max = min(more_mul_max,
DIV_ROUND_UP(limits->max_pll_multiplier, mul));
dev_dbg(dev, "more_mul_max: min_pll_multiplier check: %u\n",
more_mul_max);
/* Ensure we won't go below min_pll_op_freq_hz. */
more_mul_min = DIV_ROUND_UP(limits->min_pll_op_freq_hz,
pll->ext_clk_freq_hz / pll->pre_pll_clk_div
* mul);
dev_dbg(dev, "more_mul_min: min_pll_op_freq_hz check: %u\n",
more_mul_min);
/* Ensure we won't go below min_pll_multiplier. */
more_mul_min = max(more_mul_min,
DIV_ROUND_UP(limits->min_pll_multiplier, mul));
dev_dbg(dev, "more_mul_min: min_pll_multiplier check: %u\n",
more_mul_min);
if (more_mul_min > more_mul_max) {
dev_dbg(dev,
"unable to compute more_mul_min and more_mul_max\n");
return -EINVAL;
}
more_mul_factor = lcm(div, pll->pre_pll_clk_div) / div;
dev_dbg(dev, "more_mul_factor: %u\n", more_mul_factor);
more_mul_factor = lcm(more_mul_factor, op_limits->min_sys_clk_div);
dev_dbg(dev, "more_mul_factor: min_op_sys_clk_div: %d\n",
more_mul_factor);
i = roundup(more_mul_min, more_mul_factor);
if (!is_one_or_even(i))
i <<= 1;
dev_dbg(dev, "final more_mul: %u\n", i);
if (i > more_mul_max) {
dev_dbg(dev, "final more_mul is bad, max %u\n", more_mul_max);
return -EINVAL;
}
pll->pll_multiplier = mul * i;
op_pll->sys_clk_div = div * i / pll->pre_pll_clk_div;
dev_dbg(dev, "op_sys_clk_div: %u\n", op_pll->sys_clk_div);
pll->pll_ip_clk_freq_hz = pll->ext_clk_freq_hz
/ pll->pre_pll_clk_div;
pll->pll_op_clk_freq_hz = pll->pll_ip_clk_freq_hz
* pll->pll_multiplier;
/* Derive pll_op_clk_freq_hz. */
op_pll->sys_clk_freq_hz =
pll->pll_op_clk_freq_hz / op_pll->sys_clk_div;
op_pll->pix_clk_div = pll->bits_per_pixel;
dev_dbg(dev, "op_pix_clk_div: %u\n", op_pll->pix_clk_div);
op_pll->pix_clk_freq_hz =
op_pll->sys_clk_freq_hz / op_pll->pix_clk_div;
if (pll->flags & SMIAPP_PLL_FLAG_NO_OP_CLOCKS) {
/* No OP clocks --- VT clocks are used instead. */
goto out_skip_vt_calc;
}
/*
* Some sensors perform analogue binning and some do this
* digitally. The ones doing this digitally can be roughly be
* found out using this formula. The ones doing this digitally
* should run at higher clock rate, so smaller divisor is used
* on video timing side.
*/
if (limits->min_line_length_pck_bin > limits->min_line_length_pck
/ pll->binning_horizontal)
vt_op_binning_div = pll->binning_horizontal;
else
vt_op_binning_div = 1;
dev_dbg(dev, "vt_op_binning_div: %u\n", vt_op_binning_div);
/*
* Profile 2 supports vt_pix_clk_div E [4, 10]
*
* Horizontal binning can be used as a base for difference in
* divisors. One must make sure that horizontal blanking is
* enough to accommodate the CSI-2 sync codes.
*
* Take scaling factor into account as well.
*
* Find absolute limits for the factor of vt divider.
*/
dev_dbg(dev, "scale_m: %u\n", pll->scale_m);
min_vt_div = DIV_ROUND_UP(op_pll->pix_clk_div * op_pll->sys_clk_div
* pll->scale_n,
lane_op_clock_ratio * vt_op_binning_div
* pll->scale_m);
/* Find smallest and biggest allowed vt divisor. */
dev_dbg(dev, "min_vt_div: %u\n", min_vt_div);
min_vt_div = max(min_vt_div,
DIV_ROUND_UP(pll->pll_op_clk_freq_hz,
limits->vt.max_pix_clk_freq_hz));
dev_dbg(dev, "min_vt_div: max_vt_pix_clk_freq_hz: %u\n",
min_vt_div);
min_vt_div = max_t(uint32_t, min_vt_div,
limits->vt.min_pix_clk_div
* limits->vt.min_sys_clk_div);
dev_dbg(dev, "min_vt_div: min_vt_clk_div: %u\n", min_vt_div);
max_vt_div = limits->vt.max_sys_clk_div * limits->vt.max_pix_clk_div;
dev_dbg(dev, "max_vt_div: %u\n", max_vt_div);
max_vt_div = min(max_vt_div,
DIV_ROUND_UP(pll->pll_op_clk_freq_hz,
limits->vt.min_pix_clk_freq_hz));
dev_dbg(dev, "max_vt_div: min_vt_pix_clk_freq_hz: %u\n",
max_vt_div);
/*
* Find limitsits for sys_clk_div. Not all values are possible
* with all values of pix_clk_div.
*/
min_sys_div = limits->vt.min_sys_clk_div;
dev_dbg(dev, "min_sys_div: %u\n", min_sys_div);
min_sys_div = max(min_sys_div,
DIV_ROUND_UP(min_vt_div,
limits->vt.max_pix_clk_div));
dev_dbg(dev, "min_sys_div: max_vt_pix_clk_div: %u\n", min_sys_div);
min_sys_div = max(min_sys_div,
pll->pll_op_clk_freq_hz
/ limits->vt.max_sys_clk_freq_hz);
dev_dbg(dev, "min_sys_div: max_pll_op_clk_freq_hz: %u\n", min_sys_div);
min_sys_div = clk_div_even_up(min_sys_div);
dev_dbg(dev, "min_sys_div: one or even: %u\n", min_sys_div);
max_sys_div = limits->vt.max_sys_clk_div;
dev_dbg(dev, "max_sys_div: %u\n", max_sys_div);
max_sys_div = min(max_sys_div,
DIV_ROUND_UP(max_vt_div,
limits->vt.min_pix_clk_div));
dev_dbg(dev, "max_sys_div: min_vt_pix_clk_div: %u\n", max_sys_div);
max_sys_div = min(max_sys_div,
DIV_ROUND_UP(pll->pll_op_clk_freq_hz,
limits->vt.min_pix_clk_freq_hz));
dev_dbg(dev, "max_sys_div: min_vt_pix_clk_freq_hz: %u\n", max_sys_div);
/*
* Find pix_div such that a legal pix_div * sys_div results
* into a value which is not smaller than div, the desired
* divisor.
*/
for (vt_div = min_vt_div; vt_div <= max_vt_div;
vt_div += 2 - (vt_div & 1)) {
for (sys_div = min_sys_div;
sys_div <= max_sys_div;
sys_div += 2 - (sys_div & 1)) {
uint16_t pix_div = DIV_ROUND_UP(vt_div, sys_div);
if (pix_div < limits->vt.min_pix_clk_div
|| pix_div > limits->vt.max_pix_clk_div) {
dev_dbg(dev,
"pix_div %u too small or too big (%u--%u)\n",
pix_div,
limits->vt.min_pix_clk_div,
limits->vt.max_pix_clk_div);
continue;
}
/* Check if this one is better. */
if (pix_div * sys_div
<= roundup(min_vt_div, best_pix_div))
best_pix_div = pix_div;
}
if (best_pix_div < INT_MAX >> 1)
break;
}
pll->vt.sys_clk_div = DIV_ROUND_UP(min_vt_div, best_pix_div);
pll->vt.pix_clk_div = best_pix_div;
pll->vt.sys_clk_freq_hz =
pll->pll_op_clk_freq_hz / pll->vt.sys_clk_div;
pll->vt.pix_clk_freq_hz =
pll->vt.sys_clk_freq_hz / pll->vt.pix_clk_div;
out_skip_vt_calc:
pll->pixel_rate_csi =
op_pll->pix_clk_freq_hz * lane_op_clock_ratio;
pll->pixel_rate_pixel_array = pll->vt.pix_clk_freq_hz;
return check_all_bounds(dev, limits, op_limits, pll, op_pll);
}
int smiapp_pll_calculate(struct device *dev,
const struct smiapp_pll_limits *limits,
struct smiapp_pll *pll)
{
const struct smiapp_pll_branch_limits *op_limits = &limits->op;
struct smiapp_pll_branch *op_pll = &pll->op;
uint16_t min_pre_pll_clk_div;
uint16_t max_pre_pll_clk_div;
uint32_t lane_op_clock_ratio;
@ -386,13 +409,23 @@ int smiapp_pll_calculate(struct device *dev,
unsigned int i;
int rval = -EINVAL;
if (pll->flags & SMIAPP_PLL_FLAG_NO_OP_CLOCKS) {
/*
* If there's no OP PLL at all, use the VT values
* instead. The OP values are ignored for the rest of
* the PLL calculation.
*/
op_limits = &limits->vt;
op_pll = &pll->vt;
}
if (pll->flags & SMIAPP_PLL_FLAG_OP_PIX_CLOCK_PER_LANE)
lane_op_clock_ratio = pll->csi2.lanes;
else
lane_op_clock_ratio = 1;
dev_dbg(dev, "lane_op_clock_ratio: %d\n", lane_op_clock_ratio);
dev_dbg(dev, "lane_op_clock_ratio: %u\n", lane_op_clock_ratio);
dev_dbg(dev, "binning: %dx%d\n", pll->binning_horizontal,
dev_dbg(dev, "binning: %ux%u\n", pll->binning_horizontal,
pll->binning_vertical);
switch (pll->bus_type) {
@ -411,7 +444,7 @@ int smiapp_pll_calculate(struct device *dev,
}
/* Figure out limits for pre-pll divider based on extclk */
dev_dbg(dev, "min / max pre_pll_clk_div: %d / %d\n",
dev_dbg(dev, "min / max pre_pll_clk_div: %u / %u\n",
limits->min_pre_pll_clk_div, limits->max_pre_pll_clk_div);
max_pre_pll_clk_div =
min_t(uint16_t, limits->max_pre_pll_clk_div,
@ -422,26 +455,27 @@ int smiapp_pll_calculate(struct device *dev,
clk_div_even_up(
DIV_ROUND_UP(pll->ext_clk_freq_hz,
limits->max_pll_ip_freq_hz)));
dev_dbg(dev, "pre-pll check: min / max pre_pll_clk_div: %d / %d\n",
dev_dbg(dev, "pre-pll check: min / max pre_pll_clk_div: %u / %u\n",
min_pre_pll_clk_div, max_pre_pll_clk_div);
i = gcd(pll->pll_op_clk_freq_hz, pll->ext_clk_freq_hz);
mul = div_u64(pll->pll_op_clk_freq_hz, i);
div = pll->ext_clk_freq_hz / i;
dev_dbg(dev, "mul %d / div %d\n", mul, div);
dev_dbg(dev, "mul %u / div %u\n", mul, div);
min_pre_pll_clk_div =
max_t(uint16_t, min_pre_pll_clk_div,
clk_div_even_up(
DIV_ROUND_UP(mul * pll->ext_clk_freq_hz,
limits->max_pll_op_freq_hz)));
dev_dbg(dev, "pll_op check: min / max pre_pll_clk_div: %d / %d\n",
dev_dbg(dev, "pll_op check: min / max pre_pll_clk_div: %u / %u\n",
min_pre_pll_clk_div, max_pre_pll_clk_div);
for (pll->pre_pll_clk_div = min_pre_pll_clk_div;
pll->pre_pll_clk_div <= max_pre_pll_clk_div;
pll->pre_pll_clk_div += 2 - (pll->pre_pll_clk_div & 1)) {
rval = __smiapp_pll_calculate(dev, limits, pll, mul, div,
rval = __smiapp_pll_calculate(dev, limits, op_limits, pll,
op_pll, mul, div,
lane_op_clock_ratio);
if (rval)
continue;

View file

@ -35,6 +35,13 @@
#define SMIAPP_PLL_FLAG_OP_PIX_CLOCK_PER_LANE (1 << 0)
#define SMIAPP_PLL_FLAG_NO_OP_CLOCKS (1 << 1)
struct smiapp_pll_branch {
uint16_t sys_clk_div;
uint16_t pix_clk_div;
uint32_t sys_clk_freq_hz;
uint32_t pix_clk_freq_hz;
};
struct smiapp_pll {
/* input values */
uint8_t bus_type;
@ -53,24 +60,18 @@ struct smiapp_pll {
uint8_t scale_n;
uint8_t bits_per_pixel;
uint32_t link_freq;
uint32_t ext_clk_freq_hz;
/* output values */
uint16_t pre_pll_clk_div;
uint16_t pll_multiplier;
uint16_t op_sys_clk_div;
uint16_t op_pix_clk_div;
uint16_t vt_sys_clk_div;
uint16_t vt_pix_clk_div;
uint32_t ext_clk_freq_hz;
uint32_t pll_ip_clk_freq_hz;
uint32_t pll_op_clk_freq_hz;
uint32_t op_sys_clk_freq_hz;
uint32_t op_pix_clk_freq_hz;
uint32_t vt_sys_clk_freq_hz;
uint32_t vt_pix_clk_freq_hz;
struct smiapp_pll_branch vt;
struct smiapp_pll_branch op;
uint32_t pixel_rate_csi;
uint32_t pixel_rate_pixel_array;
};
struct smiapp_pll_branch_limits {

View file

@ -205,12 +205,12 @@ static int smiapp_pll_configure(struct smiapp_sensor *sensor)
int rval;
rval = smiapp_write(
sensor, SMIAPP_REG_U16_VT_PIX_CLK_DIV, pll->vt_pix_clk_div);
sensor, SMIAPP_REG_U16_VT_PIX_CLK_DIV, pll->vt.pix_clk_div);
if (rval < 0)
return rval;
rval = smiapp_write(
sensor, SMIAPP_REG_U16_VT_SYS_CLK_DIV, pll->vt_sys_clk_div);
sensor, SMIAPP_REG_U16_VT_SYS_CLK_DIV, pll->vt.sys_clk_div);
if (rval < 0)
return rval;
@ -227,20 +227,21 @@ static int smiapp_pll_configure(struct smiapp_sensor *sensor)
/* Lane op clock ratio does not apply here. */
rval = smiapp_write(
sensor, SMIAPP_REG_U32_REQUESTED_LINK_BIT_RATE_MBPS,
DIV_ROUND_UP(pll->op_sys_clk_freq_hz, 1000000 / 256 / 256));
DIV_ROUND_UP(pll->op.sys_clk_freq_hz, 1000000 / 256 / 256));
if (rval < 0 || sensor->minfo.smiapp_profile == SMIAPP_PROFILE_0)
return rval;
rval = smiapp_write(
sensor, SMIAPP_REG_U16_OP_PIX_CLK_DIV, pll->op_pix_clk_div);
sensor, SMIAPP_REG_U16_OP_PIX_CLK_DIV, pll->op.pix_clk_div);
if (rval < 0)
return rval;
return smiapp_write(
sensor, SMIAPP_REG_U16_OP_SYS_CLK_DIV, pll->op_sys_clk_div);
sensor, SMIAPP_REG_U16_OP_SYS_CLK_DIV, pll->op.sys_clk_div);
}
static int smiapp_pll_update(struct smiapp_sensor *sensor)
static int smiapp_pll_try(struct smiapp_sensor *sensor,
struct smiapp_pll *pll)
{
struct i2c_client *client = v4l2_get_subdevdata(&sensor->src->sd);
struct smiapp_pll_limits lim = {
@ -274,19 +275,15 @@ static int smiapp_pll_update(struct smiapp_sensor *sensor)
.min_line_length_pck_bin = sensor->limits[SMIAPP_LIMIT_MIN_LINE_LENGTH_PCK_BIN],
.min_line_length_pck = sensor->limits[SMIAPP_LIMIT_MIN_LINE_LENGTH_PCK],
};
return smiapp_pll_calculate(&client->dev, &lim, pll);
}
static int smiapp_pll_update(struct smiapp_sensor *sensor)
{
struct smiapp_pll *pll = &sensor->pll;
int rval;
if (sensor->minfo.smiapp_profile == SMIAPP_PROFILE_0) {
/*
* Fill in operational clock divisors limits from the
* video timing ones. On profile 0 sensors the
* requirements regarding them are essentially the
* same as on VT ones.
*/
lim.op = lim.vt;
}
pll->binning_horizontal = sensor->binning_horizontal;
pll->binning_vertical = sensor->binning_vertical;
pll->link_freq =
@ -294,12 +291,12 @@ static int smiapp_pll_update(struct smiapp_sensor *sensor)
pll->scale_m = sensor->scale_m;
pll->bits_per_pixel = sensor->csi_format->compressed;
rval = smiapp_pll_calculate(&client->dev, &lim, pll);
rval = smiapp_pll_try(sensor, pll);
if (rval < 0)
return rval;
__v4l2_ctrl_s_ctrl_int64(sensor->pixel_rate_parray,
pll->vt_pix_clk_freq_hz);
pll->pixel_rate_pixel_array);
__v4l2_ctrl_s_ctrl_int64(sensor->pixel_rate_csi, pll->pixel_rate_csi);
return 0;
@ -333,22 +330,22 @@ static void __smiapp_update_exposure_limits(struct smiapp_sensor *sensor)
* orders must be defined.
*/
static const struct smiapp_csi_data_format smiapp_csi_data_formats[] = {
{ V4L2_MBUS_FMT_SGRBG12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_GRBG, },
{ V4L2_MBUS_FMT_SRGGB12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_RGGB, },
{ V4L2_MBUS_FMT_SBGGR12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_BGGR, },
{ V4L2_MBUS_FMT_SGBRG12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_GBRG, },
{ V4L2_MBUS_FMT_SGRBG10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_GRBG, },
{ V4L2_MBUS_FMT_SRGGB10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_RGGB, },
{ V4L2_MBUS_FMT_SBGGR10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_BGGR, },
{ V4L2_MBUS_FMT_SGBRG10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_GBRG, },
{ V4L2_MBUS_FMT_SGRBG10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_GRBG, },
{ V4L2_MBUS_FMT_SRGGB10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_RGGB, },
{ V4L2_MBUS_FMT_SBGGR10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_BGGR, },
{ V4L2_MBUS_FMT_SGBRG10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_GBRG, },
{ V4L2_MBUS_FMT_SGRBG8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_GRBG, },
{ V4L2_MBUS_FMT_SRGGB8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_RGGB, },
{ V4L2_MBUS_FMT_SBGGR8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_BGGR, },
{ V4L2_MBUS_FMT_SGBRG8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_GBRG, },
{ MEDIA_BUS_FMT_SGRBG12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_GRBG, },
{ MEDIA_BUS_FMT_SRGGB12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_RGGB, },
{ MEDIA_BUS_FMT_SBGGR12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_BGGR, },
{ MEDIA_BUS_FMT_SGBRG12_1X12, 12, 12, SMIAPP_PIXEL_ORDER_GBRG, },
{ MEDIA_BUS_FMT_SGRBG10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_GRBG, },
{ MEDIA_BUS_FMT_SRGGB10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_RGGB, },
{ MEDIA_BUS_FMT_SBGGR10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_BGGR, },
{ MEDIA_BUS_FMT_SGBRG10_1X10, 10, 10, SMIAPP_PIXEL_ORDER_GBRG, },
{ MEDIA_BUS_FMT_SGRBG10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_GRBG, },
{ MEDIA_BUS_FMT_SRGGB10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_RGGB, },
{ MEDIA_BUS_FMT_SBGGR10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_BGGR, },
{ MEDIA_BUS_FMT_SGBRG10_DPCM8_1X8, 10, 8, SMIAPP_PIXEL_ORDER_GBRG, },
{ MEDIA_BUS_FMT_SGRBG8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_GRBG, },
{ MEDIA_BUS_FMT_SRGGB8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_RGGB, },
{ MEDIA_BUS_FMT_SBGGR8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_BGGR, },
{ MEDIA_BUS_FMT_SGBRG8_1X8, 8, 8, SMIAPP_PIXEL_ORDER_GBRG, },
};
const char *pixel_order_str[] = { "GRBG", "RGGB", "BGGR", "GBRG" };
@ -526,6 +523,8 @@ static const struct v4l2_ctrl_ops smiapp_ctrl_ops = {
static int smiapp_init_controls(struct smiapp_sensor *sensor)
{
struct i2c_client *client = v4l2_get_subdevdata(&sensor->src->sd);
unsigned long *valid_link_freqs = &sensor->valid_link_freqs[
sensor->csi_format->compressed - SMIAPP_COMPRESSED_BASE];
unsigned int max, i;
int rval;
@ -608,8 +607,8 @@ static int smiapp_init_controls(struct smiapp_sensor *sensor)
sensor->link_freq = v4l2_ctrl_new_int_menu(
&sensor->src->ctrl_handler, &smiapp_ctrl_ops,
V4L2_CID_LINK_FREQ, max, 0,
sensor->platform_data->op_sys_clock);
V4L2_CID_LINK_FREQ, __fls(*valid_link_freqs),
__ffs(*valid_link_freqs), sensor->platform_data->op_sys_clock);
sensor->pixel_rate_csi = v4l2_ctrl_new_std(
&sensor->src->ctrl_handler, &smiapp_ctrl_ops,
@ -745,6 +744,7 @@ static int smiapp_get_limits_binning(struct smiapp_sensor *sensor)
static int smiapp_get_mbus_formats(struct smiapp_sensor *sensor)
{
struct i2c_client *client = v4l2_get_subdevdata(&sensor->src->sd);
struct smiapp_pll *pll = &sensor->pll;
unsigned int type, n;
unsigned int i, pixel_order;
int rval;
@ -808,14 +808,57 @@ static int smiapp_get_mbus_formats(struct smiapp_sensor *sensor)
dev_dbg(&client->dev, "jolly good! %d\n", j);
sensor->default_mbus_frame_fmts |= 1 << j;
if (!sensor->csi_format
|| f->width > sensor->csi_format->width
|| (f->width == sensor->csi_format->width
&& f->compressed
> sensor->csi_format->compressed)) {
sensor->csi_format = f;
sensor->internal_csi_format = f;
}
}
}
/* Figure out which BPP values can be used with which formats. */
pll->binning_horizontal = 1;
pll->binning_vertical = 1;
pll->scale_m = sensor->scale_m;
for (i = 0; i < ARRAY_SIZE(smiapp_csi_data_formats); i++) {
const struct smiapp_csi_data_format *f =
&smiapp_csi_data_formats[i];
unsigned long *valid_link_freqs =
&sensor->valid_link_freqs[
f->compressed - SMIAPP_COMPRESSED_BASE];
unsigned int j;
BUG_ON(f->compressed < SMIAPP_COMPRESSED_BASE);
BUG_ON(f->compressed > SMIAPP_COMPRESSED_MAX);
if (!(sensor->default_mbus_frame_fmts & 1 << i))
continue;
pll->bits_per_pixel = f->compressed;
for (j = 0; sensor->platform_data->op_sys_clock[j]; j++) {
pll->link_freq = sensor->platform_data->op_sys_clock[j];
rval = smiapp_pll_try(sensor, pll);
dev_dbg(&client->dev, "link freq %u Hz, bpp %u %s\n",
pll->link_freq, pll->bits_per_pixel,
rval ? "not ok" : "ok");
if (rval)
continue;
set_bit(j, valid_link_freqs);
}
if (!*valid_link_freqs) {
dev_info(&client->dev,
"no valid link frequencies for %u bpp\n",
f->compressed);
sensor->default_mbus_frame_fmts &= ~BIT(i);
continue;
}
if (!sensor->csi_format
|| f->width > sensor->csi_format->width
|| (f->width == sensor->csi_format->width
&& f->compressed > sensor->csi_format->compressed)) {
sensor->csi_format = f;
sensor->internal_csi_format = f;
}
}
@ -904,7 +947,7 @@ static int smiapp_update_mode(struct smiapp_sensor *sensor)
dev_dbg(&client->dev, "hblank\t\t%d\n", sensor->hblank->val);
dev_dbg(&client->dev, "real timeperframe\t100/%d\n",
sensor->pll.vt_pix_clk_freq_hz /
sensor->pll.pixel_rate_pixel_array /
((sensor->pixel_array->crop[SMIAPP_PA_PAD_SRC].width
+ sensor->hblank->val) *
(sensor->pixel_array->crop[SMIAPP_PA_PAD_SRC].height
@ -1687,6 +1730,59 @@ static const struct smiapp_csi_data_format
return csi_format;
}
static int smiapp_set_format_source(struct v4l2_subdev *subdev,
struct v4l2_subdev_fh *fh,
struct v4l2_subdev_format *fmt)
{
struct smiapp_sensor *sensor = to_smiapp_sensor(subdev);
const struct smiapp_csi_data_format *csi_format,
*old_csi_format = sensor->csi_format;
unsigned long *valid_link_freqs;
u32 code = fmt->format.code;
unsigned int i;
int rval;
rval = __smiapp_get_format(subdev, fh, fmt);
if (rval)
return rval;
/*
* Media bus code is changeable on src subdev's source pad. On
* other source pads we just get format here.
*/
if (subdev != &sensor->src->sd)
return 0;
csi_format = smiapp_validate_csi_data_format(sensor, code);
fmt->format.code = csi_format->code;
if (fmt->which != V4L2_SUBDEV_FORMAT_ACTIVE)
return 0;
sensor->csi_format = csi_format;
if (csi_format->width != old_csi_format->width)
for (i = 0; i < ARRAY_SIZE(sensor->test_data); i++)
__v4l2_ctrl_modify_range(
sensor->test_data[i], 0,
(1 << csi_format->width) - 1, 1, 0);
if (csi_format->compressed == old_csi_format->compressed)
return 0;
valid_link_freqs =
&sensor->valid_link_freqs[sensor->csi_format->compressed
- SMIAPP_COMPRESSED_BASE];
__v4l2_ctrl_modify_range(
sensor->link_freq, 0,
__fls(*valid_link_freqs), ~*valid_link_freqs,
__ffs(*valid_link_freqs));
return smiapp_pll_update(sensor);
}
static int smiapp_set_format(struct v4l2_subdev *subdev,
struct v4l2_subdev_fh *fh,
struct v4l2_subdev_format *fmt)
@ -1697,41 +1793,14 @@ static int smiapp_set_format(struct v4l2_subdev *subdev,
mutex_lock(&sensor->mutex);
/*
* Media bus code is changeable on src subdev's source pad. On
* other source pads we just get format here.
*/
if (fmt->pad == ssd->source_pad) {
u32 code = fmt->format.code;
int rval = __smiapp_get_format(subdev, fh, fmt);
bool range_changed = false;
unsigned int i;
int rval;
if (!rval && subdev == &sensor->src->sd) {
const struct smiapp_csi_data_format *csi_format =
smiapp_validate_csi_data_format(sensor, code);
if (fmt->which == V4L2_SUBDEV_FORMAT_ACTIVE) {
if (csi_format->width !=
sensor->csi_format->width)
range_changed = true;
sensor->csi_format = csi_format;
}
fmt->format.code = csi_format->code;
}
rval = smiapp_set_format_source(subdev, fh, fmt);
mutex_unlock(&sensor->mutex);
if (rval || !range_changed)
return rval;
for (i = 0; i < ARRAY_SIZE(sensor->test_data); i++)
v4l2_ctrl_modify_range(
sensor->test_data[i],
0, (1 << sensor->csi_format->width) - 1, 1, 0);
return 0;
return rval;
}
/* Sink pad. Width and height are changeable here. */
@ -2023,6 +2092,11 @@ static int __smiapp_sel_supported(struct v4l2_subdev *subdev,
== SMIAPP_DIGITAL_CROP_CAPABILITY_INPUT_CROP)
return 0;
return -EINVAL;
case V4L2_SEL_TGT_NATIVE_SIZE:
if (ssd == sensor->pixel_array
&& sel->pad == SMIAPP_PA_PAD_SRC)
return 0;
return -EINVAL;
case V4L2_SEL_TGT_COMPOSE:
case V4L2_SEL_TGT_COMPOSE_BOUNDS:
if (sel->pad == ssd->source_pad)
@ -2121,7 +2195,9 @@ static int __smiapp_get_selection(struct v4l2_subdev *subdev,
switch (sel->target) {
case V4L2_SEL_TGT_CROP_BOUNDS:
case V4L2_SEL_TGT_NATIVE_SIZE:
if (ssd == sensor->pixel_array) {
sel->r.left = sel->r.top = 0;
sel->r.width =
sensor->limits[SMIAPP_LIMIT_X_ADDR_MAX] + 1;
sel->r.height =
@ -2482,12 +2558,6 @@ static int smiapp_registered(struct v4l2_subdev *subdev)
goto out_power_off;
}
rval = smiapp_get_mbus_formats(sensor);
if (rval) {
rval = -ENODEV;
goto out_power_off;
}
if (sensor->limits[SMIAPP_LIMIT_BINNING_CAPABILITY]) {
u32 val;
@ -2569,6 +2639,22 @@ static int smiapp_registered(struct v4l2_subdev *subdev)
sensor->scale_m = sensor->limits[SMIAPP_LIMIT_SCALER_N_MIN];
/* prepare PLL configuration input values */
pll->bus_type = SMIAPP_PLL_BUS_TYPE_CSI2;
pll->csi2.lanes = sensor->platform_data->lanes;
pll->ext_clk_freq_hz = sensor->platform_data->ext_clk;
pll->flags = smiapp_call_quirk(sensor, pll_flags);
pll->scale_n = sensor->limits[SMIAPP_LIMIT_SCALER_N_MIN];
/* Profile 0 sensors have no separate OP clock branch. */
if (sensor->minfo.smiapp_profile == SMIAPP_PROFILE_0)
pll->flags |= SMIAPP_PLL_FLAG_NO_OP_CLOCKS;
rval = smiapp_get_mbus_formats(sensor);
if (rval) {
rval = -ENODEV;
goto out_nvm_release;
}
for (i = 0; i < SMIAPP_SUBDEVS; i++) {
struct {
struct smiapp_subdev *ssd;
@ -2666,18 +2752,9 @@ static int smiapp_registered(struct v4l2_subdev *subdev)
if (rval < 0)
goto out_nvm_release;
/* prepare PLL configuration input values */
pll->bus_type = SMIAPP_PLL_BUS_TYPE_CSI2;
pll->csi2.lanes = sensor->platform_data->lanes;
pll->ext_clk_freq_hz = sensor->platform_data->ext_clk;
pll->flags = smiapp_call_quirk(sensor, pll_flags);
/* Profile 0 sensors have no separate OP clock branch. */
if (sensor->minfo.smiapp_profile == SMIAPP_PROFILE_0)
pll->flags |= SMIAPP_PLL_FLAG_NO_OP_CLOCKS;
pll->scale_n = sensor->limits[SMIAPP_LIMIT_SCALER_N_MIN];
mutex_lock(&sensor->mutex);
rval = smiapp_update_mode(sensor);
mutex_unlock(&sensor->mutex);
if (rval) {
dev_err(&client->dev, "update mode failed\n");
goto out_nvm_release;

View file

@ -156,6 +156,11 @@ struct smiapp_csi_data_format {
#define SMIAPP_PAD_SRC 1
#define SMIAPP_PADS 2
#define SMIAPP_COMPRESSED_BASE 8
#define SMIAPP_COMPRESSED_MAX 12
#define SMIAPP_NR_OF_COMPRESSED (SMIAPP_COMPRESSED_MAX - \
SMIAPP_COMPRESSED_BASE + 1)
struct smiapp_binning_subtype {
u8 horizontal:4;
u8 vertical:4;
@ -232,6 +237,9 @@ struct smiapp_sensor {
struct smiapp_pll pll;
/* Is a default format supported for a given BPP? */
unsigned long valid_link_freqs[SMIAPP_NR_OF_COMPRESSED];
/* Pixel array controls */
struct v4l2_ctrl *analog_gain;
struct v4l2_ctrl *exposure;

View file

@ -71,7 +71,7 @@
/* IMX074 has only one fixed colorspace per pixelcode */
struct imx074_datafmt {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
};
@ -82,7 +82,7 @@ struct imx074 {
};
static const struct imx074_datafmt imx074_colour_fmts[] = {
{V4L2_MBUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
};
static struct imx074 *to_imx074(const struct i2c_client *client)
@ -91,7 +91,7 @@ static struct imx074 *to_imx074(const struct i2c_client *client)
}
/* Find a data format by a pixel code in an array */
static const struct imx074_datafmt *imx074_find_datafmt(enum v4l2_mbus_pixelcode code)
static const struct imx074_datafmt *imx074_find_datafmt(u32 code)
{
int i;
@ -236,7 +236,7 @@ static int imx074_cropcap(struct v4l2_subdev *sd, struct v4l2_cropcap *a)
}
static int imx074_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if ((unsigned int)index >= ARRAY_SIZE(imx074_colour_fmts))
return -EINVAL;

View file

@ -53,13 +53,13 @@
/* MT9M001 has only one fixed colorspace per pixelcode */
struct mt9m001_datafmt {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
};
/* Find a data format by a pixel code in an array */
static const struct mt9m001_datafmt *mt9m001_find_datafmt(
enum v4l2_mbus_pixelcode code, const struct mt9m001_datafmt *fmt,
u32 code, const struct mt9m001_datafmt *fmt,
int n)
{
int i;
@ -75,14 +75,14 @@ static const struct mt9m001_datafmt mt9m001_colour_fmts[] = {
* Order important: first natively supported,
* second supported with a GPIO extender
*/
{V4L2_MBUS_FMT_SBGGR10_1X10, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_1X10, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
};
static const struct mt9m001_datafmt mt9m001_monochrome_fmts[] = {
/* Order important - see above */
{V4L2_MBUS_FMT_Y10_1X10, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_Y8_1X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_Y10_1X10, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_Y8_1X8, V4L2_COLORSPACE_JPEG},
};
struct mt9m001 {
@ -563,7 +563,7 @@ static struct v4l2_subdev_core_ops mt9m001_subdev_core_ops = {
};
static int mt9m001_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
struct i2c_client *client = v4l2_get_subdevdata(sd);
struct mt9m001 *mt9m001 = to_mt9m001(client);

View file

@ -182,23 +182,23 @@ static struct mt9m111_context context_b = {
/* MT9M111 has only one fixed colorspace per pixelcode */
struct mt9m111_datafmt {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
};
static const struct mt9m111_datafmt mt9m111_colour_fmts[] = {
{V4L2_MBUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_YVYU8_2X8, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_UYVY8_2X8, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_RGB555_2X8_PADHI_BE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_RGB565_2X8_LE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_BGR565_2X8_LE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_BGR565_2X8_BE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_YVYU8_2X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_UYVY8_2X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_VYUY8_2X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_RGB555_2X8_PADHI_BE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_RGB565_2X8_LE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_BGR565_2X8_LE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_BGR565_2X8_BE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE, V4L2_COLORSPACE_SRGB},
};
struct mt9m111 {
@ -218,7 +218,7 @@ struct mt9m111 {
/* Find a data format by a pixel code */
static const struct mt9m111_datafmt *mt9m111_find_datafmt(struct mt9m111 *mt9m111,
enum v4l2_mbus_pixelcode code)
u32 code)
{
int i;
for (i = 0; i < ARRAY_SIZE(mt9m111_colour_fmts); i++)
@ -331,7 +331,7 @@ static int mt9m111_setup_rect_ctx(struct mt9m111 *mt9m111,
}
static int mt9m111_setup_geometry(struct mt9m111 *mt9m111, struct v4l2_rect *rect,
int width, int height, enum v4l2_mbus_pixelcode code)
int width, int height, u32 code)
{
struct i2c_client *client = v4l2_get_subdevdata(&mt9m111->subdev);
int ret;
@ -345,7 +345,7 @@ static int mt9m111_setup_geometry(struct mt9m111 *mt9m111, struct v4l2_rect *rec
if (!ret)
ret = reg_write(WINDOW_HEIGHT, rect->height);
if (code != V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE) {
if (code != MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE) {
/* IFP in use, down-scaling possible */
if (!ret)
ret = mt9m111_setup_rect_ctx(mt9m111, &context_b,
@ -393,8 +393,8 @@ static int mt9m111_s_crop(struct v4l2_subdev *sd, const struct v4l2_crop *a)
if (a->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
return -EINVAL;
if (mt9m111->fmt->code == V4L2_MBUS_FMT_SBGGR8_1X8 ||
mt9m111->fmt->code == V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE) {
if (mt9m111->fmt->code == MEDIA_BUS_FMT_SBGGR8_1X8 ||
mt9m111->fmt->code == MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE) {
/* Bayer format - even size lengths */
rect.width = ALIGN(rect.width, 2);
rect.height = ALIGN(rect.height, 2);
@ -462,7 +462,7 @@ static int mt9m111_g_fmt(struct v4l2_subdev *sd,
}
static int mt9m111_set_pixfmt(struct mt9m111 *mt9m111,
enum v4l2_mbus_pixelcode code)
u32 code)
{
struct i2c_client *client = v4l2_get_subdevdata(&mt9m111->subdev);
u16 data_outfmt2, mask_outfmt2 = MT9M111_OUTFMT_PROCESSED_BAYER |
@ -474,46 +474,46 @@ static int mt9m111_set_pixfmt(struct mt9m111 *mt9m111,
int ret;
switch (code) {
case V4L2_MBUS_FMT_SBGGR8_1X8:
case MEDIA_BUS_FMT_SBGGR8_1X8:
data_outfmt2 = MT9M111_OUTFMT_PROCESSED_BAYER |
MT9M111_OUTFMT_RGB;
break;
case V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE:
case MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE:
data_outfmt2 = MT9M111_OUTFMT_BYPASS_IFP | MT9M111_OUTFMT_RGB;
break;
case V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE:
case MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE:
data_outfmt2 = MT9M111_OUTFMT_RGB | MT9M111_OUTFMT_RGB555 |
MT9M111_OUTFMT_SWAP_YCbCr_C_Y_RGB_EVEN;
break;
case V4L2_MBUS_FMT_RGB555_2X8_PADHI_BE:
case MEDIA_BUS_FMT_RGB555_2X8_PADHI_BE:
data_outfmt2 = MT9M111_OUTFMT_RGB | MT9M111_OUTFMT_RGB555;
break;
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
data_outfmt2 = MT9M111_OUTFMT_RGB | MT9M111_OUTFMT_RGB565 |
MT9M111_OUTFMT_SWAP_YCbCr_C_Y_RGB_EVEN;
break;
case V4L2_MBUS_FMT_RGB565_2X8_BE:
case MEDIA_BUS_FMT_RGB565_2X8_BE:
data_outfmt2 = MT9M111_OUTFMT_RGB | MT9M111_OUTFMT_RGB565;
break;
case V4L2_MBUS_FMT_BGR565_2X8_BE:
case MEDIA_BUS_FMT_BGR565_2X8_BE:
data_outfmt2 = MT9M111_OUTFMT_RGB | MT9M111_OUTFMT_RGB565 |
MT9M111_OUTFMT_SWAP_YCbCr_Cb_Cr_RGB_R_B;
break;
case V4L2_MBUS_FMT_BGR565_2X8_LE:
case MEDIA_BUS_FMT_BGR565_2X8_LE:
data_outfmt2 = MT9M111_OUTFMT_RGB | MT9M111_OUTFMT_RGB565 |
MT9M111_OUTFMT_SWAP_YCbCr_C_Y_RGB_EVEN |
MT9M111_OUTFMT_SWAP_YCbCr_Cb_Cr_RGB_R_B;
break;
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
data_outfmt2 = 0;
break;
case V4L2_MBUS_FMT_VYUY8_2X8:
case MEDIA_BUS_FMT_VYUY8_2X8:
data_outfmt2 = MT9M111_OUTFMT_SWAP_YCbCr_Cb_Cr_RGB_R_B;
break;
case V4L2_MBUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
data_outfmt2 = MT9M111_OUTFMT_SWAP_YCbCr_C_Y_RGB_EVEN;
break;
case V4L2_MBUS_FMT_YVYU8_2X8:
case MEDIA_BUS_FMT_YVYU8_2X8:
data_outfmt2 = MT9M111_OUTFMT_SWAP_YCbCr_C_Y_RGB_EVEN |
MT9M111_OUTFMT_SWAP_YCbCr_Cb_Cr_RGB_R_B;
break;
@ -542,8 +542,8 @@ static int mt9m111_try_fmt(struct v4l2_subdev *sd,
fmt = mt9m111_find_datafmt(mt9m111, mf->code);
bayer = fmt->code == V4L2_MBUS_FMT_SBGGR8_1X8 ||
fmt->code == V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE;
bayer = fmt->code == MEDIA_BUS_FMT_SBGGR8_1X8 ||
fmt->code == MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE;
/*
* With Bayer format enforce even side lengths, but let the user play
@ -554,7 +554,7 @@ static int mt9m111_try_fmt(struct v4l2_subdev *sd,
rect->height = ALIGN(rect->height, 2);
}
if (fmt->code == V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE) {
if (fmt->code == MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE) {
/* IFP bypass mode, no scaling */
mf->width = rect->width;
mf->height = rect->height;
@ -840,7 +840,7 @@ static struct v4l2_subdev_core_ops mt9m111_subdev_core_ops = {
};
static int mt9m111_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(mt9m111_colour_fmts))
return -EINVAL;

View file

@ -345,7 +345,7 @@ static int mt9t031_g_fmt(struct v4l2_subdev *sd,
mf->width = mt9t031->rect.width / mt9t031->xskip;
mf->height = mt9t031->rect.height / mt9t031->yskip;
mf->code = V4L2_MBUS_FMT_SBGGR10_1X10;
mf->code = MEDIA_BUS_FMT_SBGGR10_1X10;
mf->colorspace = V4L2_COLORSPACE_SRGB;
mf->field = V4L2_FIELD_NONE;
@ -367,7 +367,7 @@ static int mt9t031_s_fmt(struct v4l2_subdev *sd,
xskip = mt9t031_skip(&rect.width, mf->width, MT9T031_MAX_WIDTH);
yskip = mt9t031_skip(&rect.height, mf->height, MT9T031_MAX_HEIGHT);
mf->code = V4L2_MBUS_FMT_SBGGR10_1X10;
mf->code = MEDIA_BUS_FMT_SBGGR10_1X10;
mf->colorspace = V4L2_COLORSPACE_SRGB;
/* mt9t031_set_params() doesn't change width and height */
@ -385,7 +385,7 @@ static int mt9t031_try_fmt(struct v4l2_subdev *sd,
&mf->width, MT9T031_MIN_WIDTH, MT9T031_MAX_WIDTH, 1,
&mf->height, MT9T031_MIN_HEIGHT, MT9T031_MAX_HEIGHT, 1, 0);
mf->code = V4L2_MBUS_FMT_SBGGR10_1X10;
mf->code = MEDIA_BUS_FMT_SBGGR10_1X10;
mf->colorspace = V4L2_COLORSPACE_SRGB;
return 0;
@ -673,12 +673,12 @@ static struct v4l2_subdev_core_ops mt9t031_subdev_core_ops = {
};
static int mt9t031_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index)
return -EINVAL;
*code = V4L2_MBUS_FMT_SBGGR10_1X10;
*code = MEDIA_BUS_FMT_SBGGR10_1X10;
return 0;
}

View file

@ -77,7 +77,7 @@
struct
************************************************************************/
struct mt9t112_format {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
u16 fmt;
u16 order;
@ -103,32 +103,32 @@ struct mt9t112_priv {
static const struct mt9t112_format mt9t112_cfmts[] = {
{
.code = V4L2_MBUS_FMT_UYVY8_2X8,
.code = MEDIA_BUS_FMT_UYVY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.fmt = 1,
.order = 0,
}, {
.code = V4L2_MBUS_FMT_VYUY8_2X8,
.code = MEDIA_BUS_FMT_VYUY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.fmt = 1,
.order = 1,
}, {
.code = V4L2_MBUS_FMT_YUYV8_2X8,
.code = MEDIA_BUS_FMT_YUYV8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.fmt = 1,
.order = 2,
}, {
.code = V4L2_MBUS_FMT_YVYU8_2X8,
.code = MEDIA_BUS_FMT_YVYU8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.fmt = 1,
.order = 3,
}, {
.code = V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE,
.code = MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE,
.colorspace = V4L2_COLORSPACE_SRGB,
.fmt = 8,
.order = 2,
}, {
.code = V4L2_MBUS_FMT_RGB565_2X8_LE,
.code = MEDIA_BUS_FMT_RGB565_2X8_LE,
.colorspace = V4L2_COLORSPACE_SRGB,
.fmt = 4,
.order = 2,
@ -840,7 +840,7 @@ static int mt9t112_s_stream(struct v4l2_subdev *sd, int enable)
static int mt9t112_set_params(struct mt9t112_priv *priv,
const struct v4l2_rect *rect,
enum v4l2_mbus_pixelcode code)
u32 code)
{
int i;
@ -953,7 +953,7 @@ static int mt9t112_try_fmt(struct v4l2_subdev *sd,
break;
if (i == priv->num_formats) {
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
mf->colorspace = V4L2_COLORSPACE_JPEG;
} else {
mf->colorspace = mt9t112_cfmts[i].colorspace;
@ -967,7 +967,7 @@ static int mt9t112_try_fmt(struct v4l2_subdev *sd,
}
static int mt9t112_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
struct i2c_client *client = v4l2_get_subdevdata(sd);
struct mt9t112_priv *priv = to_mt9t112(client);
@ -1101,7 +1101,7 @@ static int mt9t112_probe(struct i2c_client *client,
/* Cannot fail: using the default supported pixel code */
if (!ret)
mt9t112_set_params(priv, &rect, V4L2_MBUS_FMT_UYVY8_2X8);
mt9t112_set_params(priv, &rect, MEDIA_BUS_FMT_UYVY8_2X8);
else
v4l2_clk_put(priv->clk);

View file

@ -85,13 +85,13 @@ MODULE_PARM_DESC(sensor_type, "Sensor type: \"colour\" or \"monochrome\"");
/* MT9V022 has only one fixed colorspace per pixelcode */
struct mt9v022_datafmt {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
};
/* Find a data format by a pixel code in an array */
static const struct mt9v022_datafmt *mt9v022_find_datafmt(
enum v4l2_mbus_pixelcode code, const struct mt9v022_datafmt *fmt,
u32 code, const struct mt9v022_datafmt *fmt,
int n)
{
int i;
@ -107,14 +107,14 @@ static const struct mt9v022_datafmt mt9v022_colour_fmts[] = {
* Order important: first natively supported,
* second supported with a GPIO extender
*/
{V4L2_MBUS_FMT_SBGGR10_1X10, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_1X10, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR8_1X8, V4L2_COLORSPACE_SRGB},
};
static const struct mt9v022_datafmt mt9v022_monochrome_fmts[] = {
/* Order important - see above */
{V4L2_MBUS_FMT_Y10_1X10, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_Y8_1X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_Y10_1X10, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_Y8_1X8, V4L2_COLORSPACE_JPEG},
};
/* only registers with different addresses on different mt9v02x sensors */
@ -410,13 +410,13 @@ static int mt9v022_s_fmt(struct v4l2_subdev *sd,
* .try_mbus_fmt(), datawidth is from our supported format list
*/
switch (mf->code) {
case V4L2_MBUS_FMT_Y8_1X8:
case V4L2_MBUS_FMT_Y10_1X10:
case MEDIA_BUS_FMT_Y8_1X8:
case MEDIA_BUS_FMT_Y10_1X10:
if (mt9v022->model != MT9V022IX7ATM)
return -EINVAL;
break;
case V4L2_MBUS_FMT_SBGGR8_1X8:
case V4L2_MBUS_FMT_SBGGR10_1X10:
case MEDIA_BUS_FMT_SBGGR8_1X8:
case MEDIA_BUS_FMT_SBGGR10_1X10:
if (mt9v022->model != MT9V022IX7ATC)
return -EINVAL;
break;
@ -443,8 +443,8 @@ static int mt9v022_try_fmt(struct v4l2_subdev *sd,
struct i2c_client *client = v4l2_get_subdevdata(sd);
struct mt9v022 *mt9v022 = to_mt9v022(client);
const struct mt9v022_datafmt *fmt;
int align = mf->code == V4L2_MBUS_FMT_SBGGR8_1X8 ||
mf->code == V4L2_MBUS_FMT_SBGGR10_1X10;
int align = mf->code == MEDIA_BUS_FMT_SBGGR8_1X8 ||
mf->code == MEDIA_BUS_FMT_SBGGR10_1X10;
v4l_bound_align_image(&mf->width, MT9V022_MIN_WIDTH,
MT9V022_MAX_WIDTH, align,
@ -759,7 +759,7 @@ static struct v4l2_subdev_core_ops mt9v022_subdev_core_ops = {
};
static int mt9v022_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
struct i2c_client *client = v4l2_get_subdevdata(sd);
struct mt9v022 *mt9v022 = to_mt9v022(client);

View file

@ -302,7 +302,7 @@ struct ov2640_win_size {
struct ov2640_priv {
struct v4l2_subdev subdev;
struct v4l2_ctrl_handler hdl;
enum v4l2_mbus_pixelcode cfmt_code;
u32 cfmt_code;
struct v4l2_clk *clk;
const struct ov2640_win_size *win;
};
@ -623,11 +623,11 @@ static const struct regval_list ov2640_rgb565_le_regs[] = {
ENDMARKER,
};
static enum v4l2_mbus_pixelcode ov2640_codes[] = {
V4L2_MBUS_FMT_YUYV8_2X8,
V4L2_MBUS_FMT_UYVY8_2X8,
V4L2_MBUS_FMT_RGB565_2X8_BE,
V4L2_MBUS_FMT_RGB565_2X8_LE,
static u32 ov2640_codes[] = {
MEDIA_BUS_FMT_YUYV8_2X8,
MEDIA_BUS_FMT_UYVY8_2X8,
MEDIA_BUS_FMT_RGB565_2X8_BE,
MEDIA_BUS_FMT_RGB565_2X8_LE,
};
/*
@ -785,7 +785,7 @@ static const struct ov2640_win_size *ov2640_select_win(u32 *width, u32 *height)
}
static int ov2640_set_params(struct i2c_client *client, u32 *width, u32 *height,
enum v4l2_mbus_pixelcode code)
u32 code)
{
struct ov2640_priv *priv = to_ov2640(client);
const struct regval_list *selected_cfmt_regs;
@ -797,20 +797,20 @@ static int ov2640_set_params(struct i2c_client *client, u32 *width, u32 *height,
/* select format */
priv->cfmt_code = 0;
switch (code) {
case V4L2_MBUS_FMT_RGB565_2X8_BE:
case MEDIA_BUS_FMT_RGB565_2X8_BE:
dev_dbg(&client->dev, "%s: Selected cfmt RGB565 BE", __func__);
selected_cfmt_regs = ov2640_rgb565_be_regs;
break;
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
dev_dbg(&client->dev, "%s: Selected cfmt RGB565 LE", __func__);
selected_cfmt_regs = ov2640_rgb565_le_regs;
break;
case V4L2_MBUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
dev_dbg(&client->dev, "%s: Selected cfmt YUYV (YUV422)", __func__);
selected_cfmt_regs = ov2640_yuyv_regs;
break;
default:
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
dev_dbg(&client->dev, "%s: Selected cfmt UYVY", __func__);
selected_cfmt_regs = ov2640_uyvy_regs;
}
@ -869,7 +869,7 @@ static int ov2640_g_fmt(struct v4l2_subdev *sd,
if (!priv->win) {
u32 width = W_SVGA, height = H_SVGA;
priv->win = ov2640_select_win(&width, &height);
priv->cfmt_code = V4L2_MBUS_FMT_UYVY8_2X8;
priv->cfmt_code = MEDIA_BUS_FMT_UYVY8_2X8;
}
mf->width = priv->win->width;
@ -877,13 +877,13 @@ static int ov2640_g_fmt(struct v4l2_subdev *sd,
mf->code = priv->cfmt_code;
switch (mf->code) {
case V4L2_MBUS_FMT_RGB565_2X8_BE:
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_BE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
mf->colorspace = V4L2_COLORSPACE_SRGB;
break;
default:
case V4L2_MBUS_FMT_YUYV8_2X8:
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
mf->colorspace = V4L2_COLORSPACE_JPEG;
}
mf->field = V4L2_FIELD_NONE;
@ -899,14 +899,14 @@ static int ov2640_s_fmt(struct v4l2_subdev *sd,
switch (mf->code) {
case V4L2_MBUS_FMT_RGB565_2X8_BE:
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_BE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
mf->colorspace = V4L2_COLORSPACE_SRGB;
break;
default:
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
case V4L2_MBUS_FMT_YUYV8_2X8:
case V4L2_MBUS_FMT_UYVY8_2X8:
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
case MEDIA_BUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
mf->colorspace = V4L2_COLORSPACE_JPEG;
}
@ -926,14 +926,14 @@ static int ov2640_try_fmt(struct v4l2_subdev *sd,
mf->field = V4L2_FIELD_NONE;
switch (mf->code) {
case V4L2_MBUS_FMT_RGB565_2X8_BE:
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_BE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
mf->colorspace = V4L2_COLORSPACE_SRGB;
break;
default:
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
case V4L2_MBUS_FMT_YUYV8_2X8:
case V4L2_MBUS_FMT_UYVY8_2X8:
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
case MEDIA_BUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
mf->colorspace = V4L2_COLORSPACE_JPEG;
}
@ -941,7 +941,7 @@ static int ov2640_try_fmt(struct v4l2_subdev *sd,
}
static int ov2640_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(ov2640_codes))
return -EINVAL;

View file

@ -602,7 +602,7 @@ static struct regval_list ov5642_default_regs_finalise[] = {
};
struct ov5642_datafmt {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
};
@ -618,7 +618,7 @@ struct ov5642 {
};
static const struct ov5642_datafmt ov5642_colour_fmts[] = {
{V4L2_MBUS_FMT_UYVY8_2X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_UYVY8_2X8, V4L2_COLORSPACE_JPEG},
};
static struct ov5642 *to_ov5642(const struct i2c_client *client)
@ -628,7 +628,7 @@ static struct ov5642 *to_ov5642(const struct i2c_client *client)
/* Find a data format by a pixel code in an array */
static const struct ov5642_datafmt
*ov5642_find_datafmt(enum v4l2_mbus_pixelcode code)
*ov5642_find_datafmt(u32 code)
{
int i;
@ -840,7 +840,7 @@ static int ov5642_g_fmt(struct v4l2_subdev *sd,
}
static int ov5642_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(ov5642_colour_fmts))
return -EINVAL;

View file

@ -202,18 +202,18 @@ struct ov6650 {
unsigned long pclk_limit; /* from host */
unsigned long pclk_max; /* from resolution and format */
struct v4l2_fract tpf; /* as requested with s_parm */
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
};
static enum v4l2_mbus_pixelcode ov6650_codes[] = {
V4L2_MBUS_FMT_YUYV8_2X8,
V4L2_MBUS_FMT_UYVY8_2X8,
V4L2_MBUS_FMT_YVYU8_2X8,
V4L2_MBUS_FMT_VYUY8_2X8,
V4L2_MBUS_FMT_SBGGR8_1X8,
V4L2_MBUS_FMT_Y8_1X8,
static u32 ov6650_codes[] = {
MEDIA_BUS_FMT_YUYV8_2X8,
MEDIA_BUS_FMT_UYVY8_2X8,
MEDIA_BUS_FMT_YVYU8_2X8,
MEDIA_BUS_FMT_VYUY8_2X8,
MEDIA_BUS_FMT_SBGGR8_1X8,
MEDIA_BUS_FMT_Y8_1X8,
};
/* read a register */
@ -555,29 +555,29 @@ static int ov6650_s_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf)
.height = mf->height << half_scale,
},
};
enum v4l2_mbus_pixelcode code = mf->code;
u32 code = mf->code;
unsigned long mclk, pclk;
u8 coma_set = 0, coma_mask = 0, coml_set, coml_mask, clkrc;
int ret;
/* select color matrix configuration for given color encoding */
switch (code) {
case V4L2_MBUS_FMT_Y8_1X8:
case MEDIA_BUS_FMT_Y8_1X8:
dev_dbg(&client->dev, "pixel format GREY8_1X8\n");
coma_mask |= COMA_RGB | COMA_WORD_SWAP | COMA_BYTE_SWAP;
coma_set |= COMA_BW;
break;
case V4L2_MBUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
dev_dbg(&client->dev, "pixel format YUYV8_2X8_LE\n");
coma_mask |= COMA_RGB | COMA_BW | COMA_BYTE_SWAP;
coma_set |= COMA_WORD_SWAP;
break;
case V4L2_MBUS_FMT_YVYU8_2X8:
case MEDIA_BUS_FMT_YVYU8_2X8:
dev_dbg(&client->dev, "pixel format YVYU8_2X8_LE (untested)\n");
coma_mask |= COMA_RGB | COMA_BW | COMA_WORD_SWAP |
COMA_BYTE_SWAP;
break;
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
dev_dbg(&client->dev, "pixel format YUYV8_2X8_BE\n");
if (half_scale) {
coma_mask |= COMA_RGB | COMA_BW | COMA_WORD_SWAP;
@ -587,7 +587,7 @@ static int ov6650_s_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf)
coma_set |= COMA_BYTE_SWAP | COMA_WORD_SWAP;
}
break;
case V4L2_MBUS_FMT_VYUY8_2X8:
case MEDIA_BUS_FMT_VYUY8_2X8:
dev_dbg(&client->dev, "pixel format YVYU8_2X8_BE (untested)\n");
if (half_scale) {
coma_mask |= COMA_RGB | COMA_BW;
@ -597,7 +597,7 @@ static int ov6650_s_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf)
coma_set |= COMA_BYTE_SWAP;
}
break;
case V4L2_MBUS_FMT_SBGGR8_1X8:
case MEDIA_BUS_FMT_SBGGR8_1X8:
dev_dbg(&client->dev, "pixel format SBGGR8_1X8 (untested)\n");
coma_mask |= COMA_BW | COMA_BYTE_SWAP | COMA_WORD_SWAP;
coma_set |= COMA_RAW_RGB | COMA_RGB;
@ -608,8 +608,8 @@ static int ov6650_s_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf)
}
priv->code = code;
if (code == V4L2_MBUS_FMT_Y8_1X8 ||
code == V4L2_MBUS_FMT_SBGGR8_1X8) {
if (code == MEDIA_BUS_FMT_Y8_1X8 ||
code == MEDIA_BUS_FMT_SBGGR8_1X8) {
coml_mask = COML_ONE_CHANNEL;
coml_set = 0;
priv->pclk_max = 4000000;
@ -619,7 +619,7 @@ static int ov6650_s_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf)
priv->pclk_max = 8000000;
}
if (code == V4L2_MBUS_FMT_SBGGR8_1X8)
if (code == MEDIA_BUS_FMT_SBGGR8_1X8)
priv->colorspace = V4L2_COLORSPACE_SRGB;
else if (code != 0)
priv->colorspace = V4L2_COLORSPACE_JPEG;
@ -697,18 +697,18 @@ static int ov6650_try_fmt(struct v4l2_subdev *sd,
mf->field = V4L2_FIELD_NONE;
switch (mf->code) {
case V4L2_MBUS_FMT_Y10_1X10:
mf->code = V4L2_MBUS_FMT_Y8_1X8;
case V4L2_MBUS_FMT_Y8_1X8:
case V4L2_MBUS_FMT_YVYU8_2X8:
case V4L2_MBUS_FMT_YUYV8_2X8:
case V4L2_MBUS_FMT_VYUY8_2X8:
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_Y10_1X10:
mf->code = MEDIA_BUS_FMT_Y8_1X8;
case MEDIA_BUS_FMT_Y8_1X8:
case MEDIA_BUS_FMT_YVYU8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_VYUY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
mf->colorspace = V4L2_COLORSPACE_JPEG;
break;
default:
mf->code = V4L2_MBUS_FMT_SBGGR8_1X8;
case V4L2_MBUS_FMT_SBGGR8_1X8:
mf->code = MEDIA_BUS_FMT_SBGGR8_1X8;
case MEDIA_BUS_FMT_SBGGR8_1X8:
mf->colorspace = V4L2_COLORSPACE_SRGB;
break;
}
@ -717,7 +717,7 @@ static int ov6650_try_fmt(struct v4l2_subdev *sd,
}
static int ov6650_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(ov6650_codes))
return -EINVAL;
@ -1013,7 +1013,7 @@ static int ov6650_probe(struct i2c_client *client,
priv->rect.width = W_CIF;
priv->rect.height = H_CIF;
priv->half_scale = false;
priv->code = V4L2_MBUS_FMT_YUYV8_2X8;
priv->code = MEDIA_BUS_FMT_YUYV8_2X8;
priv->colorspace = V4L2_COLORSPACE_JPEG;
priv->clk = v4l2_clk_get(&client->dev, "mclk");

View file

@ -376,7 +376,7 @@
*/
struct ov772x_color_format {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
u8 dsp3;
u8 dsp4;
@ -408,7 +408,7 @@ struct ov772x_priv {
*/
static const struct ov772x_color_format ov772x_cfmts[] = {
{
.code = V4L2_MBUS_FMT_YUYV8_2X8,
.code = MEDIA_BUS_FMT_YUYV8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.dsp3 = 0x0,
.dsp4 = DSP_OFMT_YUV,
@ -416,7 +416,7 @@ static const struct ov772x_color_format ov772x_cfmts[] = {
.com7 = OFMT_YUV,
},
{
.code = V4L2_MBUS_FMT_YVYU8_2X8,
.code = MEDIA_BUS_FMT_YVYU8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.dsp3 = UV_ON,
.dsp4 = DSP_OFMT_YUV,
@ -424,7 +424,7 @@ static const struct ov772x_color_format ov772x_cfmts[] = {
.com7 = OFMT_YUV,
},
{
.code = V4L2_MBUS_FMT_UYVY8_2X8,
.code = MEDIA_BUS_FMT_UYVY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.dsp3 = 0x0,
.dsp4 = DSP_OFMT_YUV,
@ -432,7 +432,7 @@ static const struct ov772x_color_format ov772x_cfmts[] = {
.com7 = OFMT_YUV,
},
{
.code = V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE,
.code = MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE,
.colorspace = V4L2_COLORSPACE_SRGB,
.dsp3 = 0x0,
.dsp4 = DSP_OFMT_YUV,
@ -440,7 +440,7 @@ static const struct ov772x_color_format ov772x_cfmts[] = {
.com7 = FMT_RGB555 | OFMT_RGB,
},
{
.code = V4L2_MBUS_FMT_RGB555_2X8_PADHI_BE,
.code = MEDIA_BUS_FMT_RGB555_2X8_PADHI_BE,
.colorspace = V4L2_COLORSPACE_SRGB,
.dsp3 = 0x0,
.dsp4 = DSP_OFMT_YUV,
@ -448,7 +448,7 @@ static const struct ov772x_color_format ov772x_cfmts[] = {
.com7 = FMT_RGB555 | OFMT_RGB,
},
{
.code = V4L2_MBUS_FMT_RGB565_2X8_LE,
.code = MEDIA_BUS_FMT_RGB565_2X8_LE,
.colorspace = V4L2_COLORSPACE_SRGB,
.dsp3 = 0x0,
.dsp4 = DSP_OFMT_YUV,
@ -456,7 +456,7 @@ static const struct ov772x_color_format ov772x_cfmts[] = {
.com7 = FMT_RGB565 | OFMT_RGB,
},
{
.code = V4L2_MBUS_FMT_RGB565_2X8_BE,
.code = MEDIA_BUS_FMT_RGB565_2X8_BE,
.colorspace = V4L2_COLORSPACE_SRGB,
.dsp3 = 0x0,
.dsp4 = DSP_OFMT_YUV,
@ -468,7 +468,7 @@ static const struct ov772x_color_format ov772x_cfmts[] = {
* regardless of the COM7 value. We can thus only support 10-bit
* Bayer until someone figures it out.
*/
.code = V4L2_MBUS_FMT_SBGGR10_1X10,
.code = MEDIA_BUS_FMT_SBGGR10_1X10,
.colorspace = V4L2_COLORSPACE_SRGB,
.dsp3 = 0x0,
.dsp4 = DSP_OFMT_RAW10,
@ -990,7 +990,7 @@ static struct v4l2_subdev_core_ops ov772x_subdev_core_ops = {
};
static int ov772x_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(ov772x_cfmts))
return -EINVAL;

View file

@ -159,10 +159,10 @@ static const struct ov9640_reg ov9640_regs_rgb[] = {
{ OV9640_MTXS, 0x65 },
};
static enum v4l2_mbus_pixelcode ov9640_codes[] = {
V4L2_MBUS_FMT_UYVY8_2X8,
V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE,
V4L2_MBUS_FMT_RGB565_2X8_LE,
static u32 ov9640_codes[] = {
MEDIA_BUS_FMT_UYVY8_2X8,
MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE,
MEDIA_BUS_FMT_RGB565_2X8_LE,
};
/* read a register */
@ -351,22 +351,22 @@ static void ov9640_res_roundup(u32 *width, u32 *height)
}
/* Prepare necessary register changes depending on color encoding */
static void ov9640_alter_regs(enum v4l2_mbus_pixelcode code,
static void ov9640_alter_regs(u32 code,
struct ov9640_reg_alt *alt)
{
switch (code) {
default:
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
alt->com12 = OV9640_COM12_YUV_AVG;
alt->com13 = OV9640_COM13_Y_DELAY_EN |
OV9640_COM13_YUV_DLY(0x01);
break;
case V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE:
case MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE:
alt->com7 = OV9640_COM7_RGB;
alt->com13 = OV9640_COM13_RGB_AVG;
alt->com15 = OV9640_COM15_RGB_555;
break;
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
alt->com7 = OV9640_COM7_RGB;
alt->com13 = OV9640_COM13_RGB_AVG;
alt->com15 = OV9640_COM15_RGB_565;
@ -376,7 +376,7 @@ static void ov9640_alter_regs(enum v4l2_mbus_pixelcode code,
/* Setup registers according to resolution and color encoding */
static int ov9640_write_regs(struct i2c_client *client, u32 width,
enum v4l2_mbus_pixelcode code, struct ov9640_reg_alt *alts)
u32 code, struct ov9640_reg_alt *alts)
{
const struct ov9640_reg *ov9640_regs, *matrix_regs;
int ov9640_regs_len, matrix_regs_len;
@ -419,7 +419,7 @@ static int ov9640_write_regs(struct i2c_client *client, u32 width,
}
/* select color matrix configuration for given color encoding */
if (code == V4L2_MBUS_FMT_UYVY8_2X8) {
if (code == MEDIA_BUS_FMT_UYVY8_2X8) {
matrix_regs = ov9640_regs_yuv;
matrix_regs_len = ARRAY_SIZE(ov9640_regs_yuv);
} else {
@ -487,7 +487,7 @@ static int ov9640_s_fmt(struct v4l2_subdev *sd,
struct i2c_client *client = v4l2_get_subdevdata(sd);
struct ov9640_reg_alt alts = {0};
enum v4l2_colorspace cspace;
enum v4l2_mbus_pixelcode code = mf->code;
u32 code = mf->code;
int ret;
ov9640_res_roundup(&mf->width, &mf->height);
@ -500,13 +500,13 @@ static int ov9640_s_fmt(struct v4l2_subdev *sd,
return ret;
switch (code) {
case V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE:
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
cspace = V4L2_COLORSPACE_SRGB;
break;
default:
code = V4L2_MBUS_FMT_UYVY8_2X8;
case V4L2_MBUS_FMT_UYVY8_2X8:
code = MEDIA_BUS_FMT_UYVY8_2X8;
case MEDIA_BUS_FMT_UYVY8_2X8:
cspace = V4L2_COLORSPACE_JPEG;
}
@ -527,13 +527,13 @@ static int ov9640_try_fmt(struct v4l2_subdev *sd,
mf->field = V4L2_FIELD_NONE;
switch (mf->code) {
case V4L2_MBUS_FMT_RGB555_2X8_PADHI_LE:
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB555_2X8_PADHI_LE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
mf->colorspace = V4L2_COLORSPACE_SRGB;
break;
default:
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
case V4L2_MBUS_FMT_UYVY8_2X8:
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
case MEDIA_BUS_FMT_UYVY8_2X8:
mf->colorspace = V4L2_COLORSPACE_JPEG;
}
@ -541,7 +541,7 @@ static int ov9640_try_fmt(struct v4l2_subdev *sd,
}
static int ov9640_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(ov9640_codes))
return -EINVAL;

View file

@ -392,8 +392,8 @@ static const struct ov9740_reg ov9740_defaults[] = {
{ OV9740_ISP_CTRL19, 0x02 },
};
static enum v4l2_mbus_pixelcode ov9740_codes[] = {
V4L2_MBUS_FMT_YUYV8_2X8,
static u32 ov9740_codes[] = {
MEDIA_BUS_FMT_YUYV8_2X8,
};
/* read a register */
@ -674,13 +674,13 @@ static int ov9740_s_fmt(struct v4l2_subdev *sd,
struct i2c_client *client = v4l2_get_subdevdata(sd);
struct ov9740_priv *priv = to_ov9740(sd);
enum v4l2_colorspace cspace;
enum v4l2_mbus_pixelcode code = mf->code;
u32 code = mf->code;
int ret;
ov9740_res_roundup(&mf->width, &mf->height);
switch (code) {
case V4L2_MBUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
cspace = V4L2_COLORSPACE_SRGB;
break;
default:
@ -710,14 +710,14 @@ static int ov9740_try_fmt(struct v4l2_subdev *sd,
ov9740_res_roundup(&mf->width, &mf->height);
mf->field = V4L2_FIELD_NONE;
mf->code = V4L2_MBUS_FMT_YUYV8_2X8;
mf->code = MEDIA_BUS_FMT_YUYV8_2X8;
mf->colorspace = V4L2_COLORSPACE_SRGB;
return 0;
}
static int ov9740_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(ov9740_codes))
return -EINVAL;

View file

@ -111,13 +111,13 @@
/* RJ54N1CB0C has only one fixed colorspace per pixelcode */
struct rj54n1_datafmt {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
};
/* Find a data format by a pixel code in an array */
static const struct rj54n1_datafmt *rj54n1_find_datafmt(
enum v4l2_mbus_pixelcode code, const struct rj54n1_datafmt *fmt,
u32 code, const struct rj54n1_datafmt *fmt,
int n)
{
int i;
@ -129,15 +129,15 @@ static const struct rj54n1_datafmt *rj54n1_find_datafmt(
}
static const struct rj54n1_datafmt rj54n1_colour_fmts[] = {
{V4L2_MBUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_YVYU8_2X8, V4L2_COLORSPACE_JPEG},
{V4L2_MBUS_FMT_RGB565_2X8_LE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR10_2X8_PADLO_LE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_BE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR10_2X8_PADLO_BE, V4L2_COLORSPACE_SRGB},
{V4L2_MBUS_FMT_SBGGR10_1X10, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_YVYU8_2X8, V4L2_COLORSPACE_JPEG},
{MEDIA_BUS_FMT_RGB565_2X8_LE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_RGB565_2X8_BE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_2X8_PADLO_LE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_BE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_2X8_PADLO_BE, V4L2_COLORSPACE_SRGB},
{MEDIA_BUS_FMT_SBGGR10_1X10, V4L2_COLORSPACE_SRGB},
};
struct rj54n1_clock_div {
@ -486,7 +486,7 @@ static int reg_write_multiple(struct i2c_client *client,
}
static int rj54n1_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(rj54n1_colour_fmts))
return -EINVAL;
@ -965,11 +965,11 @@ static int rj54n1_try_fmt(struct v4l2_subdev *sd,
struct i2c_client *client = v4l2_get_subdevdata(sd);
struct rj54n1 *rj54n1 = to_rj54n1(client);
const struct rj54n1_datafmt *fmt;
int align = mf->code == V4L2_MBUS_FMT_SBGGR10_1X10 ||
mf->code == V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_BE ||
mf->code == V4L2_MBUS_FMT_SBGGR10_2X8_PADLO_BE ||
mf->code == V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE ||
mf->code == V4L2_MBUS_FMT_SBGGR10_2X8_PADLO_LE;
int align = mf->code == MEDIA_BUS_FMT_SBGGR10_1X10 ||
mf->code == MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_BE ||
mf->code == MEDIA_BUS_FMT_SBGGR10_2X8_PADLO_BE ||
mf->code == MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE ||
mf->code == MEDIA_BUS_FMT_SBGGR10_2X8_PADLO_LE;
dev_dbg(&client->dev, "%s: code = %d, width = %u, height = %u\n",
__func__, mf->code, mf->width, mf->height);
@ -1025,55 +1025,55 @@ static int rj54n1_s_fmt(struct v4l2_subdev *sd,
/* RA_SEL_UL is only relevant for raw modes, ignored otherwise. */
switch (mf->code) {
case V4L2_MBUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
ret = reg_write(client, RJ54N1_OUT_SEL, 0);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 8, 8);
break;
case V4L2_MBUS_FMT_YVYU8_2X8:
case MEDIA_BUS_FMT_YVYU8_2X8:
ret = reg_write(client, RJ54N1_OUT_SEL, 0);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 0, 8);
break;
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
ret = reg_write(client, RJ54N1_OUT_SEL, 0x11);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 8, 8);
break;
case V4L2_MBUS_FMT_RGB565_2X8_BE:
case MEDIA_BUS_FMT_RGB565_2X8_BE:
ret = reg_write(client, RJ54N1_OUT_SEL, 0x11);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 0, 8);
break;
case V4L2_MBUS_FMT_SBGGR10_2X8_PADLO_LE:
case MEDIA_BUS_FMT_SBGGR10_2X8_PADLO_LE:
ret = reg_write(client, RJ54N1_OUT_SEL, 4);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 8, 8);
if (!ret)
ret = reg_write(client, RJ54N1_RA_SEL_UL, 0);
break;
case V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_LE:
case MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_LE:
ret = reg_write(client, RJ54N1_OUT_SEL, 4);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 8, 8);
if (!ret)
ret = reg_write(client, RJ54N1_RA_SEL_UL, 8);
break;
case V4L2_MBUS_FMT_SBGGR10_2X8_PADLO_BE:
case MEDIA_BUS_FMT_SBGGR10_2X8_PADLO_BE:
ret = reg_write(client, RJ54N1_OUT_SEL, 4);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 0, 8);
if (!ret)
ret = reg_write(client, RJ54N1_RA_SEL_UL, 0);
break;
case V4L2_MBUS_FMT_SBGGR10_2X8_PADHI_BE:
case MEDIA_BUS_FMT_SBGGR10_2X8_PADHI_BE:
ret = reg_write(client, RJ54N1_OUT_SEL, 4);
if (!ret)
ret = reg_set(client, RJ54N1_BYTE_SWAP, 0, 8);
if (!ret)
ret = reg_write(client, RJ54N1_RA_SEL_UL, 8);
break;
case V4L2_MBUS_FMT_SBGGR10_1X10:
case MEDIA_BUS_FMT_SBGGR10_1X10:
ret = reg_write(client, RJ54N1_OUT_SEL, 5);
break;
default:
@ -1083,7 +1083,7 @@ static int rj54n1_s_fmt(struct v4l2_subdev *sd,
/* Special case: a raw mode with 10 bits of data per clock tick */
if (!ret)
ret = reg_set(client, RJ54N1_OCLK_SEL_EN,
(mf->code == V4L2_MBUS_FMT_SBGGR10_1X10) << 1, 2);
(mf->code == MEDIA_BUS_FMT_SBGGR10_1X10) << 1, 2);
if (ret < 0)
return ret;

View file

@ -705,7 +705,7 @@ static int tw9910_g_fmt(struct v4l2_subdev *sd,
mf->width = priv->scale->width;
mf->height = priv->scale->height;
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
mf->colorspace = V4L2_COLORSPACE_JPEG;
mf->field = V4L2_FIELD_INTERLACED_BT;
@ -724,7 +724,7 @@ static int tw9910_s_fmt(struct v4l2_subdev *sd,
/*
* check color format
*/
if (mf->code != V4L2_MBUS_FMT_UYVY8_2X8)
if (mf->code != MEDIA_BUS_FMT_UYVY8_2X8)
return -EINVAL;
mf->colorspace = V4L2_COLORSPACE_JPEG;
@ -751,7 +751,7 @@ static int tw9910_try_fmt(struct v4l2_subdev *sd,
return -EINVAL;
}
mf->code = V4L2_MBUS_FMT_UYVY8_2X8;
mf->code = MEDIA_BUS_FMT_UYVY8_2X8;
mf->colorspace = V4L2_COLORSPACE_JPEG;
/*
@ -822,12 +822,12 @@ static struct v4l2_subdev_core_ops tw9910_subdev_core_ops = {
};
static int tw9910_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index)
return -EINVAL;
*code = V4L2_MBUS_FMT_UYVY8_2X8;
*code = MEDIA_BUS_FMT_UYVY8_2X8;
return 0;
}

View file

@ -165,7 +165,7 @@ struct sr030pc30_info {
};
struct sr030pc30_format {
enum v4l2_mbus_pixelcode code;
u32 code;
enum v4l2_colorspace colorspace;
u16 ispctl1_reg;
};
@ -201,23 +201,23 @@ static const struct sr030pc30_frmsize sr030pc30_sizes[] = {
/* supported pixel formats */
static const struct sr030pc30_format sr030pc30_formats[] = {
{
.code = V4L2_MBUS_FMT_YUYV8_2X8,
.code = MEDIA_BUS_FMT_YUYV8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x03,
}, {
.code = V4L2_MBUS_FMT_YVYU8_2X8,
.code = MEDIA_BUS_FMT_YVYU8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x02,
}, {
.code = V4L2_MBUS_FMT_VYUY8_2X8,
.code = MEDIA_BUS_FMT_VYUY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0,
}, {
.code = V4L2_MBUS_FMT_UYVY8_2X8,
.code = MEDIA_BUS_FMT_UYVY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x01,
}, {
.code = V4L2_MBUS_FMT_RGB565_2X8_BE,
.code = MEDIA_BUS_FMT_RGB565_2X8_BE,
.colorspace = V4L2_COLORSPACE_JPEG,
.ispctl1_reg = 0x40,
},
@ -472,7 +472,7 @@ static int sr030pc30_s_ctrl(struct v4l2_ctrl *ctrl)
}
static int sr030pc30_enum_fmt(struct v4l2_subdev *sd, unsigned int index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (!code || index >= ARRAY_SIZE(sr030pc30_formats))
return -EINVAL;

View file

@ -756,12 +756,12 @@ static int tvp514x_s_ctrl(struct v4l2_ctrl *ctrl)
*/
static int
tvp514x_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index)
return -EINVAL;
*code = V4L2_MBUS_FMT_YUYV10_2X10;
*code = MEDIA_BUS_FMT_YUYV10_2X10;
return 0;
}
@ -784,7 +784,7 @@ tvp514x_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *f)
/* Calculate height and width based on current standard */
current_std = decoder->current_std;
f->code = V4L2_MBUS_FMT_YUYV8_2X8;
f->code = MEDIA_BUS_FMT_YUYV8_2X8;
f->width = decoder->std_list[current_std].width;
f->height = decoder->std_list[current_std].height;
f->field = V4L2_FIELD_INTERLACED;
@ -942,7 +942,7 @@ static int tvp514x_enum_mbus_code(struct v4l2_subdev *sd,
if (index != 0)
return -EINVAL;
code->code = V4L2_MBUS_FMT_YUYV8_2X8;
code->code = MEDIA_BUS_FMT_YUYV8_2X8;
return 0;
}
@ -967,7 +967,7 @@ static int tvp514x_get_pad_format(struct v4l2_subdev *sd,
return 0;
}
format->format.code = V4L2_MBUS_FMT_YUYV8_2X8;
format->format.code = MEDIA_BUS_FMT_YUYV8_2X8;
format->format.width = tvp514x_std_list[decoder->current_std].width;
format->format.height = tvp514x_std_list[decoder->current_std].height;
format->format.colorspace = V4L2_COLORSPACE_SMPTE170M;
@ -991,7 +991,7 @@ static int tvp514x_set_pad_format(struct v4l2_subdev *sd,
struct tvp514x_decoder *decoder = to_decoder(sd);
if (fmt->format.field != V4L2_FIELD_INTERLACED ||
fmt->format.code != V4L2_MBUS_FMT_YUYV8_2X8 ||
fmt->format.code != MEDIA_BUS_FMT_YUYV8_2X8 ||
fmt->format.colorspace != V4L2_COLORSPACE_SMPTE170M ||
fmt->format.width != tvp514x_std_list[decoder->current_std].width ||
fmt->format.height != tvp514x_std_list[decoder->current_std].height)

View file

@ -818,12 +818,12 @@ static v4l2_std_id tvp5150_read_std(struct v4l2_subdev *sd)
}
static int tvp5150_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index)
return -EINVAL;
*code = V4L2_MBUS_FMT_UYVY8_2X8;
*code = MEDIA_BUS_FMT_UYVY8_2X8;
return 0;
}
@ -840,7 +840,7 @@ static int tvp5150_mbus_fmt(struct v4l2_subdev *sd,
f->width = decoder->rect.width;
f->height = decoder->rect.height;
f->code = V4L2_MBUS_FMT_UYVY8_2X8;
f->code = MEDIA_BUS_FMT_UYVY8_2X8;
f->field = V4L2_FIELD_SEQ_TB;
f->colorspace = V4L2_COLORSPACE_SMPTE170M;

View file

@ -626,7 +626,7 @@ static int tvp7002_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *f
f->width = bt->width;
f->height = bt->height;
f->code = V4L2_MBUS_FMT_YUYV10_1X20;
f->code = MEDIA_BUS_FMT_YUYV10_1X20;
f->field = device->current_timings->scanmode;
f->colorspace = device->current_timings->color_space;
@ -756,12 +756,12 @@ static int tvp7002_s_register(struct v4l2_subdev *sd,
*/
static int tvp7002_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
/* Check requested format index is within range */
if (index)
return -EINVAL;
*code = V4L2_MBUS_FMT_YUYV10_1X20;
*code = MEDIA_BUS_FMT_YUYV10_1X20;
return 0;
}
@ -859,7 +859,7 @@ tvp7002_enum_mbus_code(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh,
if (code->index != 0)
return -EINVAL;
code->code = V4L2_MBUS_FMT_YUYV10_1X20;
code->code = MEDIA_BUS_FMT_YUYV10_1X20;
return 0;
}
@ -878,7 +878,7 @@ tvp7002_get_pad_format(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh,
{
struct tvp7002 *tvp7002 = to_tvp7002(sd);
fmt->format.code = V4L2_MBUS_FMT_YUYV10_1X20;
fmt->format.code = MEDIA_BUS_FMT_YUYV10_1X20;
fmt->format.width = tvp7002->current_timings->timings.bt.width;
fmt->format.height = tvp7002->current_timings->timings.bt.height;
fmt->format.field = tvp7002->current_timings->scanmode;

View file

@ -45,19 +45,19 @@ struct vs6624 {
};
static const struct vs6624_format {
enum v4l2_mbus_pixelcode mbus_code;
u32 mbus_code;
enum v4l2_colorspace colorspace;
} vs6624_formats[] = {
{
.mbus_code = V4L2_MBUS_FMT_UYVY8_2X8,
.mbus_code = MEDIA_BUS_FMT_UYVY8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
},
{
.mbus_code = V4L2_MBUS_FMT_YUYV8_2X8,
.mbus_code = MEDIA_BUS_FMT_YUYV8_2X8,
.colorspace = V4L2_COLORSPACE_JPEG,
},
{
.mbus_code = V4L2_MBUS_FMT_RGB565_2X8_LE,
.mbus_code = MEDIA_BUS_FMT_RGB565_2X8_LE,
.colorspace = V4L2_COLORSPACE_SRGB,
},
};
@ -65,7 +65,7 @@ static const struct vs6624_format {
static struct v4l2_mbus_framefmt vs6624_default_fmt = {
.width = VGA_WIDTH,
.height = VGA_HEIGHT,
.code = V4L2_MBUS_FMT_UYVY8_2X8,
.code = MEDIA_BUS_FMT_UYVY8_2X8,
.field = V4L2_FIELD_NONE,
.colorspace = V4L2_COLORSPACE_JPEG,
};
@ -558,7 +558,7 @@ static int vs6624_s_ctrl(struct v4l2_ctrl *ctrl)
}
static int vs6624_enum_mbus_fmt(struct v4l2_subdev *sd, unsigned index,
enum v4l2_mbus_pixelcode *code)
u32 *code)
{
if (index >= ARRAY_SIZE(vs6624_formats))
return -EINVAL;
@ -605,15 +605,15 @@ static int vs6624_s_mbus_fmt(struct v4l2_subdev *sd,
/* set image format */
switch (fmt->code) {
case V4L2_MBUS_FMT_UYVY8_2X8:
case MEDIA_BUS_FMT_UYVY8_2X8:
vs6624_write(sd, VS6624_IMG_FMT0, 0x0);
vs6624_write(sd, VS6624_YUV_SETUP, 0x1);
break;
case V4L2_MBUS_FMT_YUYV8_2X8:
case MEDIA_BUS_FMT_YUYV8_2X8:
vs6624_write(sd, VS6624_IMG_FMT0, 0x0);
vs6624_write(sd, VS6624_YUV_SETUP, 0x3);
break;
case V4L2_MBUS_FMT_RGB565_2X8_LE:
case MEDIA_BUS_FMT_RGB565_2X8_LE:
vs6624_write(sd, VS6624_IMG_FMT0, 0x4);
vs6624_write(sd, VS6624_RGB_SETUP, 0x0);
break;

View file

@ -279,8 +279,14 @@ __must_check int media_entity_pipeline_start(struct media_entity *entity,
continue;
ret = entity->ops->link_validate(link);
if (ret < 0 && ret != -ENOIOCTLCMD)
if (ret < 0 && ret != -ENOIOCTLCMD) {
dev_dbg(entity->parent->dev,
"link validation failed for \"%s\":%u -> \"%s\":%u, error %d\n",
entity->name, link->source->index,
link->sink->entity->name,
link->sink->index, ret);
goto error;
}
}
/* Either no links or validated links are fine. */
@ -288,6 +294,11 @@ __must_check int media_entity_pipeline_start(struct media_entity *entity,
if (!bitmap_full(active, entity->num_pads)) {
ret = -EPIPE;
dev_dbg(entity->parent->dev,
"\"%s\":%u must be connected by an enabled link\n",
entity->name,
(unsigned)find_first_zero_bit(
active, entity->num_pads));
goto error;
}
}

View file

@ -46,6 +46,7 @@ source "drivers/media/pci/pt3/Kconfig"
source "drivers/media/pci/mantis/Kconfig"
source "drivers/media/pci/ngene/Kconfig"
source "drivers/media/pci/ddbridge/Kconfig"
source "drivers/media/pci/smipcie/Kconfig"
endif
endif #MEDIA_PCI_SUPPORT

View file

@ -11,7 +11,8 @@ obj-y += ttpci/ \
mantis/ \
ngene/ \
ddbridge/ \
saa7146/
saa7146/ \
smipcie/
obj-$(CONFIG_VIDEO_IVTV) += ivtv/
obj-$(CONFIG_VIDEO_ZORAN) += zoran/

View file

@ -3870,10 +3870,10 @@ static void osprey_eeprom(struct bttv *btv, const u8 ee[256])
} else {
unsigned short type;
for (i = 4*16; i < 8*16; i += 16) {
u16 checksum = ip_compute_csum(ee + i, 16);
for (i = 4 * 16; i < 8 * 16; i += 16) {
u16 checksum = (__force u16)ip_compute_csum(ee + i, 16);
if ((checksum&0xff) + (checksum>>8) == 0xff)
if ((checksum & 0xff) + (checksum >> 8) == 0xff)
break;
}
if (i >= 8*16)

View file

@ -84,7 +84,7 @@ bttv_risc_packed(struct bttv *btv, struct btcx_riscmem *risc,
continue;
while (offset && offset >= sg_dma_len(sg)) {
offset -= sg_dma_len(sg);
sg++;
sg = sg_next(sg);
}
if (bpl <= sg_dma_len(sg)-offset) {
/* fits into current chunk */
@ -100,13 +100,13 @@ bttv_risc_packed(struct bttv *btv, struct btcx_riscmem *risc,
*(rp++)=cpu_to_le32(sg_dma_address(sg)+offset);
todo -= (sg_dma_len(sg)-offset);
offset = 0;
sg++;
sg = sg_next(sg);
while (todo > sg_dma_len(sg)) {
*(rp++)=cpu_to_le32(BT848_RISC_WRITE|
sg_dma_len(sg));
*(rp++)=cpu_to_le32(sg_dma_address(sg));
todo -= sg_dma_len(sg);
sg++;
sg = sg_next(sg);
}
*(rp++)=cpu_to_le32(BT848_RISC_WRITE|BT848_RISC_EOL|
todo);
@ -187,15 +187,15 @@ bttv_risc_planar(struct bttv *btv, struct btcx_riscmem *risc,
/* go to next sg entry if needed */
while (yoffset && yoffset >= sg_dma_len(ysg)) {
yoffset -= sg_dma_len(ysg);
ysg++;
ysg = sg_next(ysg);
}
while (uoffset && uoffset >= sg_dma_len(usg)) {
uoffset -= sg_dma_len(usg);
usg++;
usg = sg_next(usg);
}
while (voffset && voffset >= sg_dma_len(vsg)) {
voffset -= sg_dma_len(vsg);
vsg++;
vsg = sg_next(vsg);
}
/* calculate max number of bytes we can write */

View file

@ -490,8 +490,8 @@ void cx18_av_std_setup(struct cx18 *cx)
/* Sets horizontal blanking delay and active lines */
cx18_av_write(cx, 0x470, hblank);
cx18_av_write(cx, 0x471, 0xff & (((hblank >> 8) & 0x3) |
(hactive << 4)));
cx18_av_write(cx, 0x471,
(((hblank >> 8) & 0x3) | (hactive << 4)) & 0xff);
cx18_av_write(cx, 0x472, hactive >> 4);
/* Sets burst gate delay */
@ -499,14 +499,14 @@ void cx18_av_std_setup(struct cx18 *cx)
/* Sets vertical blanking delay and active duration */
cx18_av_write(cx, 0x474, vblank);
cx18_av_write(cx, 0x475, 0xff & (((vblank >> 8) & 0x3) |
(vactive << 4)));
cx18_av_write(cx, 0x475,
(((vblank >> 8) & 0x3) | (vactive << 4)) & 0xff);
cx18_av_write(cx, 0x476, vactive >> 4);
cx18_av_write(cx, 0x477, vblank656);
/* Sets src decimation rate */
cx18_av_write(cx, 0x478, 0xff & src_decimation);
cx18_av_write(cx, 0x479, 0xff & (src_decimation >> 8));
cx18_av_write(cx, 0x478, src_decimation & 0xff);
cx18_av_write(cx, 0x479, (src_decimation >> 8) & 0xff);
/* Sets Luma and UV Low pass filters */
cx18_av_write(cx, 0x47a, luma_lpf << 6 | ((uv_lpf << 4) & 0x30));
@ -516,8 +516,8 @@ void cx18_av_std_setup(struct cx18 *cx)
/* Sets SC Step*/
cx18_av_write(cx, 0x47c, sc);
cx18_av_write(cx, 0x47d, 0xff & sc >> 8);
cx18_av_write(cx, 0x47e, 0xff & sc >> 16);
cx18_av_write(cx, 0x47d, (sc >> 8) & 0xff);
cx18_av_write(cx, 0x47e, (sc >> 16) & 0xff);
if (std & V4L2_STD_625_50) {
state->slicer_line_delay = 1;
@ -952,7 +952,7 @@ static int cx18_av_s_mbus_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt
int HSC, VSC, Vsrc, Hsrc, filter, Vlines;
int is_50Hz = !(state->std & V4L2_STD_525_60);
if (fmt->code != V4L2_MBUS_FMT_FIXED)
if (fmt->code != MEDIA_BUS_FMT_FIXED)
return -EINVAL;
fmt->field = V4L2_FIELD_INTERLACED;

View file

@ -57,7 +57,8 @@
/* V4L2 capability aliases */
#define CX18_CAP_ENCODER (V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_TUNER | \
V4L2_CAP_AUDIO | V4L2_CAP_READWRITE | \
V4L2_CAP_VBI_CAPTURE | V4L2_CAP_SLICED_VBI_CAPTURE)
V4L2_CAP_STREAMING | V4L2_CAP_VBI_CAPTURE | \
V4L2_CAP_SLICED_VBI_CAPTURE)
struct cx18_card_video_input {
u8 video_type; /* video input type */

View file

@ -98,7 +98,7 @@ static int cx18_s_video_encoding(struct cx2341x_handler *cxhdl, u32 val)
/* fix videodecoder resolution */
fmt.width = cxhdl->width / (is_mpeg1 ? 2 : 1);
fmt.height = cxhdl->height;
fmt.code = V4L2_MBUS_FMT_FIXED;
fmt.code = MEDIA_BUS_FMT_FIXED;
v4l2_subdev_call(cx->sd_av, video, s_mbus_fmt, &fmt);
return 0;
}

View file

@ -379,6 +379,7 @@ struct cx18_stream {
const char *name; /* name of the stream */
int type; /* stream type */
u32 handle; /* task handle */
u32 v4l2_dev_caps; /* device capabilities */
unsigned int mdl_base_idx;
u32 id;

View file

@ -294,7 +294,7 @@ static int cx18_s_fmt_vid_cap(struct file *file, void *fh,
mbus_fmt.width = cx->cxhdl.width = w;
mbus_fmt.height = cx->cxhdl.height = h;
mbus_fmt.code = V4L2_MBUS_FMT_FIXED;
mbus_fmt.code = MEDIA_BUS_FMT_FIXED;
v4l2_subdev_call(cx->sd_av, video, s_mbus_fmt, &mbus_fmt);
return cx18_g_fmt_vid_cap(file, fh, fmt);
}
@ -393,15 +393,16 @@ static int cx18_querycap(struct file *file, void *fh,
struct v4l2_capability *vcap)
{
struct cx18_open_id *id = fh2id(fh);
struct cx18_stream *s = video_drvdata(file);
struct cx18 *cx = id->cx;
strlcpy(vcap->driver, CX18_DRIVER_NAME, sizeof(vcap->driver));
strlcpy(vcap->card, cx->card_name, sizeof(vcap->card));
snprintf(vcap->bus_info, sizeof(vcap->bus_info),
"PCI:%s", pci_name(cx->pci_dev));
vcap->capabilities = cx->v4l2_cap; /* capabilities */
if (id->type == CX18_ENC_STREAM_TYPE_YUV)
vcap->capabilities |= V4L2_CAP_STREAMING;
vcap->capabilities = cx->v4l2_cap; /* capabilities */
vcap->device_caps = s->v4l2_dev_caps; /* device capabilities */
vcap->capabilities |= V4L2_CAP_DEVICE_CAPS;
return 0;
}

View file

@ -58,11 +58,14 @@ static struct {
int vfl_type;
int num_offset;
int dma;
u32 caps;
} cx18_stream_info[] = {
{ /* CX18_ENC_STREAM_TYPE_MPG */
"encoder MPEG",
VFL_TYPE_GRABBER, 0,
PCI_DMA_FROMDEVICE,
V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE |
V4L2_CAP_AUDIO | V4L2_CAP_TUNER
},
{ /* CX18_ENC_STREAM_TYPE_TS */
"TS",
@ -73,11 +76,15 @@ static struct {
"encoder YUV",
VFL_TYPE_GRABBER, CX18_V4L2_ENC_YUV_OFFSET,
PCI_DMA_FROMDEVICE,
V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE |
V4L2_CAP_STREAMING | V4L2_CAP_AUDIO | V4L2_CAP_TUNER
},
{ /* CX18_ENC_STREAM_TYPE_VBI */
"encoder VBI",
VFL_TYPE_VBI, 0,
PCI_DMA_FROMDEVICE,
V4L2_CAP_VBI_CAPTURE | V4L2_CAP_SLICED_VBI_CAPTURE |
V4L2_CAP_READWRITE | V4L2_CAP_TUNER
},
{ /* CX18_ENC_STREAM_TYPE_PCM */
"encoder PCM audio",
@ -93,6 +100,7 @@ static struct {
"encoder radio",
VFL_TYPE_RADIO, 0,
PCI_DMA_NONE,
V4L2_CAP_RADIO | V4L2_CAP_TUNER
},
};
@ -260,6 +268,7 @@ static void cx18_stream_init(struct cx18 *cx, int type)
s->handle = CX18_INVALID_TASK_HANDLE;
s->dma = cx18_stream_info[type].dma;
s->v4l2_dev_caps = cx18_stream_info[type].caps;
s->buffers = cx->stream_buffers[type];
s->buf_size = cx->stream_buf_size[type];
INIT_LIST_HEAD(&s->buf_pool);

View file

@ -1148,6 +1148,7 @@ static int queue_setup(struct vb2_queue *q, const struct v4l2_format *fmt,
dev->ts1.ts_packet_count = mpeglines;
*num_planes = 1;
sizes[0] = mpeglinesize * mpeglines;
alloc_ctxs[0] = dev->alloc_ctx;
*num_buffers = mpegbufs;
return 0;
}
@ -1166,11 +1167,8 @@ static void buffer_finish(struct vb2_buffer *vb)
struct cx23885_dev *dev = vb->vb2_queue->drv_priv;
struct cx23885_buffer *buf = container_of(vb,
struct cx23885_buffer, vb);
struct sg_table *sgt = vb2_dma_sg_plane_desc(vb, 0);
cx23885_free_buffer(dev, buf);
dma_unmap_sg(&dev->pci->dev, sgt->sgl, sgt->nents, DMA_FROM_DEVICE);
}
static void buffer_queue(struct vb2_buffer *vb)

View file

@ -680,6 +680,32 @@ struct cx23885_board cx23885_boards[] = {
.portb = CX23885_MPEG_DVB,
.portc = CX23885_MPEG_DVB,
},
[CX23885_BOARD_DVBSKY_T980C] = {
.name = "DVBSky T980C",
.portb = CX23885_MPEG_DVB,
},
[CX23885_BOARD_DVBSKY_S950C] = {
.name = "DVBSky S950C",
.portb = CX23885_MPEG_DVB,
},
[CX23885_BOARD_TT_CT2_4500_CI] = {
.name = "Technotrend TT-budget CT2-4500 CI",
.portb = CX23885_MPEG_DVB,
},
[CX23885_BOARD_DVBSKY_S950] = {
.name = "DVBSky S950",
.portb = CX23885_MPEG_DVB,
},
[CX23885_BOARD_DVBSKY_S952] = {
.name = "DVBSky S952",
.portb = CX23885_MPEG_DVB,
.portc = CX23885_MPEG_DVB,
},
[CX23885_BOARD_DVBSKY_T982] = {
.name = "DVBSky T982",
.portb = CX23885_MPEG_DVB,
.portc = CX23885_MPEG_DVB,
},
};
const unsigned int cx23885_bcount = ARRAY_SIZE(cx23885_boards);
@ -939,6 +965,30 @@ struct cx23885_subid cx23885_subids[] = {
.subvendor = 0x4254,
.subdevice = 0x9580,
.card = CX23885_BOARD_DVBSKY_T9580,
}, {
.subvendor = 0x4254,
.subdevice = 0x980c,
.card = CX23885_BOARD_DVBSKY_T980C,
}, {
.subvendor = 0x4254,
.subdevice = 0x950c,
.card = CX23885_BOARD_DVBSKY_S950C,
}, {
.subvendor = 0x13c2,
.subdevice = 0x3013,
.card = CX23885_BOARD_TT_CT2_4500_CI,
}, {
.subvendor = 0x4254,
.subdevice = 0x0950,
.card = CX23885_BOARD_DVBSKY_S950,
}, {
.subvendor = 0x4254,
.subdevice = 0x0952,
.card = CX23885_BOARD_DVBSKY_S952,
}, {
.subvendor = 0x4254,
.subdevice = 0x0982,
.card = CX23885_BOARD_DVBSKY_T982,
},
};
const unsigned int cx23885_idcount = ARRAY_SIZE(cx23885_subids);
@ -1534,6 +1584,8 @@ void cx23885_gpio_setup(struct cx23885_dev *dev)
mdelay(60);
break;
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
/* enable GPIO3-18 pins */
cx_write(MC417_CTL, 0x00000037);
cx23885_gpio_enable(dev, GPIO_2 | GPIO_11, 1);
@ -1541,6 +1593,45 @@ void cx23885_gpio_setup(struct cx23885_dev *dev)
mdelay(100);
cx23885_gpio_set(dev, GPIO_2 | GPIO_11);
break;
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
/*
* GPIO-0 INTA from CiMax, input
* GPIO-1 reset CiMax, output, high active
* GPIO-2 reset demod, output, low active
* GPIO-3 to GPIO-10 data/addr for CAM
* GPIO-11 ~CS0 to CiMax1
* GPIO-12 ~CS1 to CiMax2
* GPIO-13 ADL0 load LSB addr
* GPIO-14 ADL1 load MSB addr
* GPIO-15 ~RDY from CiMax
* GPIO-17 ~RD to CiMax
* GPIO-18 ~WR to CiMax
*/
cx_set(GP0_IO, 0x00060002); /* GPIO 1/2 as output */
cx_clear(GP0_IO, 0x00010004); /* GPIO 0 as input */
mdelay(100); /* reset delay */
cx_set(GP0_IO, 0x00060004); /* GPIO as out, reset high */
cx_clear(GP0_IO, 0x00010002);
cx_write(MC417_CTL, 0x00000037); /* enable GPIO3-18 pins */
/* GPIO-15 IN as ~ACK, rest as OUT */
cx_write(MC417_OEN, 0x00001000);
/* ~RD, ~WR high; ADL0, ADL1 low; ~CS0, ~CS1 high */
cx_write(MC417_RWD, 0x0000c300);
/* enable irq */
cx_write(GPIO_ISM, 0x00000000); /* INTERRUPTS active low */
break;
case CX23885_BOARD_DVBSKY_S950:
cx23885_gpio_enable(dev, GPIO_2, 1);
cx23885_gpio_clear(dev, GPIO_2);
msleep(100);
cx23885_gpio_set(dev, GPIO_2);
break;
}
}
@ -1621,6 +1712,13 @@ int cx23885_ir_init(struct cx23885_dev *dev)
case CX23885_BOARD_MYGICA_X8507:
case CX23885_BOARD_TBS_6980:
case CX23885_BOARD_TBS_6981:
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
if (!enable_885_ir)
break;
dev->sd_ir = cx23885_find_hw(dev, CX23885_HW_AV_CORE);
@ -1667,6 +1765,13 @@ void cx23885_ir_fini(struct cx23885_dev *dev)
case CX23885_BOARD_MYGICA_X8507:
case CX23885_BOARD_TBS_6980:
case CX23885_BOARD_TBS_6981:
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
cx23885_irq_remove(dev, PCI_MSK_AV_CORE);
/* sd_ir is a duplicate pointer to the AV Core, just clear it */
dev->sd_ir = NULL;
@ -1714,6 +1819,13 @@ void cx23885_ir_pci_int_enable(struct cx23885_dev *dev)
case CX23885_BOARD_MYGICA_X8507:
case CX23885_BOARD_TBS_6980:
case CX23885_BOARD_TBS_6981:
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
if (dev->sd_ir)
cx23885_irq_add_enable(dev, PCI_MSK_AV_CORE);
break;
@ -1817,6 +1929,10 @@ void cx23885_card_setup(struct cx23885_dev *dev)
case CX23885_BOARD_TEVII_S471:
case CX23885_BOARD_DVBWORLD_2005:
case CX23885_BOARD_PROF_8000:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
case CX23885_BOARD_DVBSKY_S950:
ts1->gen_ctrl_val = 0x5; /* Parallel */
ts1->ts_clk_en_val = 0x1; /* Enable TS_CLK */
ts1->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO;
@ -1865,6 +1981,7 @@ void cx23885_card_setup(struct cx23885_dev *dev)
ts2->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO;
break;
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T982:
ts1->gen_ctrl_val = 0x5; /* Parallel */
ts1->ts_clk_en_val = 0x1; /* Enable TS_CLK */
ts1->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO;
@ -1872,6 +1989,14 @@ void cx23885_card_setup(struct cx23885_dev *dev)
ts2->ts_clk_en_val = 0x1; /* Enable TS_CLK */
ts2->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO;
break;
case CX23885_BOARD_DVBSKY_S952:
ts1->gen_ctrl_val = 0x5; /* Parallel */
ts1->ts_clk_en_val = 0x1; /* Enable TS_CLK */
ts1->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO;
ts2->gen_ctrl_val = 0xe; /* Serial bus */
ts2->ts_clk_en_val = 0x1; /* Enable TS_CLK */
ts2->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO;
break;
case CX23885_BOARD_HAUPPAUGE_HVR1250:
case CX23885_BOARD_HAUPPAUGE_HVR1500:
case CX23885_BOARD_HAUPPAUGE_HVR1500Q:
@ -1935,6 +2060,12 @@ void cx23885_card_setup(struct cx23885_dev *dev)
case CX23885_BOARD_TBS_6980:
case CX23885_BOARD_TBS_6981:
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
dev->sd_cx25840 = v4l2_i2c_new_subdev(&dev->v4l2_dev,
&dev->i2c_bus[2].i2c_adap,
"cx25840", 0x88 >> 1, NULL);

View file

@ -1453,17 +1453,12 @@ int cx23885_buf_prepare(struct cx23885_buffer *buf, struct cx23885_tsport *port)
struct cx23885_dev *dev = port->dev;
int size = port->ts_packet_size * port->ts_packet_count;
struct sg_table *sgt = vb2_dma_sg_plane_desc(&buf->vb, 0);
int rc;
dprintk(1, "%s: %p\n", __func__, buf);
if (vb2_plane_size(&buf->vb, 0) < size)
return -EINVAL;
vb2_set_plane_payload(&buf->vb, 0, size);
rc = dma_map_sg(&dev->pci->dev, sgt->sgl, sgt->nents, DMA_FROM_DEVICE);
if (!rc)
return -EIO;
cx23885_risc_databuffer(dev->pci, &buf->risc,
sgt->sgl,
port->ts_packet_size, port->ts_packet_count, 0);
@ -1997,9 +1992,14 @@ static int cx23885_initdev(struct pci_dev *pci_dev,
if (!pci_dma_supported(pci_dev, 0xffffffff)) {
printk("%s/0: Oops: no 32bit PCI DMA ???\n", dev->name);
err = -EIO;
goto fail_irq;
goto fail_context;
}
dev->alloc_ctx = vb2_dma_sg_init_ctx(&pci_dev->dev);
if (IS_ERR(dev->alloc_ctx)) {
err = PTR_ERR(dev->alloc_ctx);
goto fail_context;
}
err = request_irq(pci_dev->irq, cx23885_irq,
IRQF_SHARED, dev->name, dev);
if (err < 0) {
@ -2028,6 +2028,8 @@ static int cx23885_initdev(struct pci_dev *pci_dev,
return 0;
fail_irq:
vb2_dma_sg_cleanup_ctx(dev->alloc_ctx);
fail_context:
cx23885_dev_unregister(dev);
fail_ctrl:
v4l2_ctrl_handler_free(hdl);
@ -2053,6 +2055,7 @@ static void cx23885_finidev(struct pci_dev *pci_dev)
free_irq(pci_dev->irq, dev);
cx23885_dev_unregister(dev);
vb2_dma_sg_cleanup_ctx(dev->alloc_ctx);
v4l2_ctrl_handler_free(&dev->ctrl_handler);
v4l2_device_unregister(v4l2_dev);
kfree(dev);

View file

@ -71,6 +71,7 @@
#include "si2165.h"
#include "si2168.h"
#include "si2157.h"
#include "sp2.h"
#include "m88ds3103.h"
#include "m88ts2022.h"
@ -101,6 +102,7 @@ static int queue_setup(struct vb2_queue *q, const struct v4l2_format *fmt,
port->ts_packet_count = 32;
*num_planes = 1;
sizes[0] = port->ts_packet_size * port->ts_packet_count;
alloc_ctxs[0] = port->dev->alloc_ctx;
*num_buffers = 32;
return 0;
}
@ -121,11 +123,8 @@ static void buffer_finish(struct vb2_buffer *vb)
struct cx23885_dev *dev = port->dev;
struct cx23885_buffer *buf = container_of(vb,
struct cx23885_buffer, vb);
struct sg_table *sgt = vb2_dma_sg_plane_desc(vb, 0);
cx23885_free_buffer(dev, buf);
dma_unmap_sg(&dev->pci->dev, sgt->sgl, sgt->nents, DMA_FROM_DEVICE);
}
static void buffer_queue(struct vb2_buffer *vb)
@ -616,6 +615,103 @@ static int dvbsky_t9580_set_voltage(struct dvb_frontend *fe,
return 0;
}
static int dvbsky_s952_portc_set_voltage(struct dvb_frontend *fe,
fe_sec_voltage_t voltage)
{
struct cx23885_tsport *port = fe->dvb->priv;
struct cx23885_dev *dev = port->dev;
cx23885_gpio_enable(dev, GPIO_12 | GPIO_13, 1);
switch (voltage) {
case SEC_VOLTAGE_13:
cx23885_gpio_set(dev, GPIO_13);
cx23885_gpio_clear(dev, GPIO_12);
break;
case SEC_VOLTAGE_18:
cx23885_gpio_set(dev, GPIO_13);
cx23885_gpio_set(dev, GPIO_12);
break;
case SEC_VOLTAGE_OFF:
cx23885_gpio_clear(dev, GPIO_13);
cx23885_gpio_clear(dev, GPIO_12);
break;
}
/* call the frontend set_voltage function */
return port->fe_set_voltage(fe, voltage);
}
static int cx23885_sp2_ci_ctrl(void *priv, u8 read, int addr,
u8 data, int *mem)
{
/* MC417 */
#define SP2_DATA 0x000000ff
#define SP2_WR 0x00008000
#define SP2_RD 0x00004000
#define SP2_ACK 0x00001000
#define SP2_ADHI 0x00000800
#define SP2_ADLO 0x00000400
#define SP2_CS1 0x00000200
#define SP2_CS0 0x00000100
#define SP2_EN_ALL 0x00001000
#define SP2_CTRL_OFF (SP2_CS1 | SP2_CS0 | SP2_WR | SP2_RD)
struct cx23885_tsport *port = priv;
struct cx23885_dev *dev = port->dev;
int ret;
int tmp = 0;
unsigned long timeout;
mutex_lock(&dev->gpio_lock);
/* write addr */
cx_write(MC417_OEN, SP2_EN_ALL);
cx_write(MC417_RWD, SP2_CTRL_OFF |
SP2_ADLO | (0xff & addr));
cx_clear(MC417_RWD, SP2_ADLO);
cx_write(MC417_RWD, SP2_CTRL_OFF |
SP2_ADHI | (0xff & (addr >> 8)));
cx_clear(MC417_RWD, SP2_ADHI);
if (read)
/* data in */
cx_write(MC417_OEN, SP2_EN_ALL | SP2_DATA);
else
/* data out */
cx_write(MC417_RWD, SP2_CTRL_OFF | data);
/* chip select 0 */
cx_clear(MC417_RWD, SP2_CS0);
/* read/write */
cx_clear(MC417_RWD, (read) ? SP2_RD : SP2_WR);
/* wait for a maximum of 1 msec */
timeout = jiffies + msecs_to_jiffies(1);
while (!time_after(jiffies, timeout)) {
tmp = cx_read(MC417_RWD);
if ((tmp & SP2_ACK) == 0)
break;
usleep_range(50, 100);
}
cx_set(MC417_RWD, SP2_CTRL_OFF);
*mem = tmp & 0xff;
mutex_unlock(&dev->gpio_lock);
if (!read) {
if (*mem < 0) {
ret = -EREMOTEIO;
goto err;
}
}
return 0;
err:
return ret;
}
static int cx23885_dvb_set_frontend(struct dvb_frontend *fe)
{
struct dtv_frontend_properties *p = &fe->dtv_property_cache;
@ -793,6 +889,32 @@ static const struct m88ds3103_config dvbsky_t9580_m88ds3103_config = {
.agc = 0x99,
};
static const struct m88ds3103_config dvbsky_s950c_m88ds3103_config = {
.i2c_addr = 0x68,
.clock = 27000000,
.i2c_wr_max = 33,
.clock_out = 0,
.ts_mode = M88DS3103_TS_CI,
.ts_clk = 10000,
.ts_clk_pol = 1,
.lnb_en_pol = 1,
.lnb_hv_pol = 0,
.agc = 0x99,
};
static const struct m88ds3103_config dvbsky_s952_portc_m88ds3103_config = {
.i2c_addr = 0x68,
.clock = 27000000,
.i2c_wr_max = 33,
.clock_out = 0,
.ts_mode = M88DS3103_TS_SERIAL,
.ts_clk = 96000,
.ts_clk_pol = 0,
.lnb_en_pol = 1,
.lnb_hv_pol = 0,
.agc = 0x99,
};
static int netup_altera_fpga_rw(void *device, int flag, int data, int read)
{
struct cx23885_dev *dev = (struct cx23885_dev *)device;
@ -944,11 +1066,13 @@ static int dvb_register(struct cx23885_tsport *port)
struct vb2_dvb_frontend *fe0, *fe1 = NULL;
struct si2168_config si2168_config;
struct si2157_config si2157_config;
struct sp2_config sp2_config;
struct m88ts2022_config m88ts2022_config;
struct i2c_board_info info;
struct i2c_adapter *adapter;
struct i2c_client *client_demod;
struct i2c_client *client_tuner;
struct i2c_client *client_demod = NULL, *client_tuner = NULL, *client_ci = NULL;
const struct m88ds3103_config *p_m88ds3103_config = NULL;
int (*p_set_voltage)(struct dvb_frontend *fe, fe_sec_voltage_t voltage) = NULL;
int mfe_shared = 0; /* bus not shared by default */
int ret;
@ -973,11 +1097,11 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(s5h1409_attach,
&hauppauge_generic_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(mt2131_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_generic_tunerconfig, 0);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(mt2131_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_generic_tunerconfig, 0);
break;
case CX23885_BOARD_HAUPPAUGE_HVR1270:
case CX23885_BOARD_HAUPPAUGE_HVR1275:
@ -985,11 +1109,11 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(lgdt3305_attach,
&hauppauge_lgdt3305_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_hvr127x_config);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_hvr127x_config);
if (dev->board == CX23885_BOARD_HAUPPAUGE_HVR1275)
cx23885_set_frontend_hook(port, fe0->dvb.frontend);
break;
@ -999,11 +1123,12 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(s5h1411_attach,
&hcw_s5h1411_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_tda18271_config);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_tda18271_config);
tda18271_attach(&dev->ts1.analog_fe,
0x60, &dev->i2c_bus[1].i2c_adap,
@ -1018,14 +1143,15 @@ static int dvb_register(struct cx23885_tsport *port)
dvb_attach(s5h1409_attach,
&hauppauge_ezqam_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(tda829x_attach, fe0->dvb.frontend,
&dev->i2c_bus[1].i2c_adap, 0x42,
&tda829x_no_probe);
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_tda18271_config);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(tda829x_attach, fe0->dvb.frontend,
&dev->i2c_bus[1].i2c_adap, 0x42,
&tda829x_no_probe);
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_tda18271_config);
break;
case 0:
default:
@ -1033,11 +1159,11 @@ static int dvb_register(struct cx23885_tsport *port)
dvb_attach(s5h1409_attach,
&hauppauge_generic_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL)
dvb_attach(mt2131_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_generic_tunerconfig, 0);
break;
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(mt2131_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_generic_tunerconfig, 0);
}
break;
case CX23885_BOARD_HAUPPAUGE_HVR1800lp:
@ -1045,32 +1171,33 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(s5h1409_attach,
&hauppauge_hvr1800lp_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(mt2131_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_generic_tunerconfig, 0);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(mt2131_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_generic_tunerconfig, 0);
break;
case CX23885_BOARD_DVICO_FUSIONHDTV_5_EXP:
i2c_bus = &dev->i2c_bus[0];
fe0->dvb.frontend = dvb_attach(lgdt330x_attach,
&fusionhdtv_5_express,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(simple_tuner_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap, 0x61,
TUNER_LG_TDVS_H06XF);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(simple_tuner_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap, 0x61,
TUNER_LG_TDVS_H06XF);
break;
case CX23885_BOARD_HAUPPAUGE_HVR1500Q:
i2c_bus = &dev->i2c_bus[1];
fe0->dvb.frontend = dvb_attach(s5h1409_attach,
&hauppauge_hvr1500q_config,
&dev->i2c_bus[0].i2c_adap);
if (fe0->dvb.frontend != NULL)
dvb_attach(xc5000_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_hvr1500q_tunerconfig);
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(xc5000_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_hvr1500q_tunerconfig);
break;
case CX23885_BOARD_HAUPPAUGE_HVR1500:
i2c_bus = &dev->i2c_bus[1];
@ -1101,14 +1228,14 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(tda10048_attach,
&hauppauge_hvr1200_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(tda829x_attach, fe0->dvb.frontend,
&dev->i2c_bus[1].i2c_adap, 0x42,
&tda829x_no_probe);
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_hvr1200_tuner_config);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(tda829x_attach, fe0->dvb.frontend,
&dev->i2c_bus[1].i2c_adap, 0x42,
&tda829x_no_probe);
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[1].i2c_adap,
&hauppauge_hvr1200_tuner_config);
break;
case CX23885_BOARD_HAUPPAUGE_HVR1210:
i2c_bus = &dev->i2c_bus[0];
@ -1367,12 +1494,10 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(lgs8gxx_attach,
&mygica_x8506_lgs8gl5_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(xc5000_attach,
fe0->dvb.frontend,
&i2c_bus2->i2c_adap,
&mygica_x8506_xc5000_config);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(xc5000_attach, fe0->dvb.frontend,
&i2c_bus2->i2c_adap, &mygica_x8506_xc5000_config);
cx23885_set_frontend_hook(port, fe0->dvb.frontend);
break;
case CX23885_BOARD_MYGICA_X8507:
@ -1381,12 +1506,12 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(mb86a20s_attach,
&mygica_x8507_mb86a20s_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(xc5000_attach,
fe0->dvb.frontend,
&i2c_bus2->i2c_adap,
&mygica_x8507_xc5000_config);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(xc5000_attach, fe0->dvb.frontend,
&i2c_bus2->i2c_adap,
&mygica_x8507_xc5000_config);
cx23885_set_frontend_hook(port, fe0->dvb.frontend);
break;
case CX23885_BOARD_MAGICPRO_PROHDTVE2:
@ -1395,12 +1520,11 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(lgs8gxx_attach,
&magicpro_prohdtve2_lgs8g75_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(xc5000_attach,
fe0->dvb.frontend,
&i2c_bus2->i2c_adap,
&magicpro_prohdtve2_xc5000_config);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(xc5000_attach, fe0->dvb.frontend,
&i2c_bus2->i2c_adap,
&magicpro_prohdtve2_xc5000_config);
cx23885_set_frontend_hook(port, fe0->dvb.frontend);
break;
case CX23885_BOARD_HAUPPAUGE_HVR1850:
@ -1408,10 +1532,11 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(s5h1411_attach,
&hcw_s5h1411_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL)
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[0].i2c_adap,
&hauppauge_tda18271_config);
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[0].i2c_adap,
&hauppauge_tda18271_config);
tda18271_attach(&dev->ts1.analog_fe,
0x60, &dev->i2c_bus[1].i2c_adap,
@ -1423,10 +1548,11 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(s5h1411_attach,
&hcw_s5h1411_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL)
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[0].i2c_adap,
&hauppauge_tda18271_config);
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(tda18271_attach, fe0->dvb.frontend,
0x60, &dev->i2c_bus[0].i2c_adap,
&hauppauge_tda18271_config);
break;
case CX23885_BOARD_MYGICA_X8558PRO:
switch (port->nr) {
@ -1436,12 +1562,11 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(atbm8830_attach,
&mygica_x8558pro_atbm8830_cfg1,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(max2165_attach,
fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&mygic_x8558pro_max2165_cfg1);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(max2165_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&mygic_x8558pro_max2165_cfg1);
break;
/* port C */
case 2:
@ -1449,13 +1574,11 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(atbm8830_attach,
&mygica_x8558pro_atbm8830_cfg2,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(max2165_attach,
fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&mygic_x8558pro_max2165_cfg2);
}
break;
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(max2165_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&mygic_x8558pro_max2165_cfg2);
}
break;
case CX23885_BOARD_NETUP_DUAL_DVB_T_C_CI_RF:
@ -1467,15 +1590,15 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(stv0367ter_attach,
&netup_stv0367_config[port->nr - 1],
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
if (NULL == dvb_attach(xc5000_attach,
fe0->dvb.frontend,
if (fe0->dvb.frontend == NULL)
break;
if (NULL == dvb_attach(xc5000_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&netup_xc5000_config[port->nr - 1]))
goto frontend_detach;
/* load xc5000 firmware */
fe0->dvb.frontend->ops.tuner_ops.init(fe0->dvb.frontend);
}
goto frontend_detach;
/* load xc5000 firmware */
fe0->dvb.frontend->ops.tuner_ops.init(fe0->dvb.frontend);
/* MFE frontend 2 */
fe1 = vb2_dvb_get_frontend(&port->frontends, 2);
if (fe1 == NULL)
@ -1484,14 +1607,15 @@ static int dvb_register(struct cx23885_tsport *port)
fe1->dvb.frontend = dvb_attach(stv0367cab_attach,
&netup_stv0367_config[port->nr - 1],
&i2c_bus->i2c_adap);
if (fe1->dvb.frontend != NULL) {
fe1->dvb.frontend->id = 1;
if (NULL == dvb_attach(xc5000_attach,
fe1->dvb.frontend,
&i2c_bus->i2c_adap,
&netup_xc5000_config[port->nr - 1]))
goto frontend_detach;
}
if (fe1->dvb.frontend == NULL)
break;
fe1->dvb.frontend->id = 1;
if (NULL == dvb_attach(xc5000_attach,
fe1->dvb.frontend,
&i2c_bus->i2c_adap,
&netup_xc5000_config[port->nr - 1]))
goto frontend_detach;
break;
case CX23885_BOARD_TERRATEC_CINERGY_T_PCIE_DUAL:
i2c_bus = &dev->i2c_bus[0];
@ -1503,26 +1627,26 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(drxk_attach,
&terratec_drxk_config[0],
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
if (!dvb_attach(mt2063_attach,
fe0->dvb.frontend,
&terratec_mt2063_config[0],
&i2c_bus2->i2c_adap))
goto frontend_detach;
}
if (fe0->dvb.frontend == NULL)
break;
if (!dvb_attach(mt2063_attach,
fe0->dvb.frontend,
&terratec_mt2063_config[0],
&i2c_bus2->i2c_adap))
goto frontend_detach;
break;
/* port c */
case 2:
fe0->dvb.frontend = dvb_attach(drxk_attach,
&terratec_drxk_config[1],
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
if (!dvb_attach(mt2063_attach,
fe0->dvb.frontend,
&terratec_mt2063_config[1],
&i2c_bus2->i2c_adap))
goto frontend_detach;
}
if (fe0->dvb.frontend == NULL)
break;
if (!dvb_attach(mt2063_attach,
fe0->dvb.frontend,
&terratec_mt2063_config[1],
&i2c_bus2->i2c_adap))
goto frontend_detach;
break;
}
break;
@ -1532,10 +1656,10 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(ds3000_attach,
&tevii_ds3000_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
dvb_attach(ts2020_attach, fe0->dvb.frontend,
&tevii_ts2020_config, &i2c_bus->i2c_adap);
}
if (fe0->dvb.frontend == NULL)
break;
dvb_attach(ts2020_attach, fe0->dvb.frontend,
&tevii_ts2020_config, &i2c_bus->i2c_adap);
break;
case CX23885_BOARD_PROF_8000:
i2c_bus = &dev->i2c_bus[0];
@ -1544,15 +1668,15 @@ static int dvb_register(struct cx23885_tsport *port)
&prof_8000_stv090x_config,
&i2c_bus->i2c_adap,
STV090x_DEMODULATOR_0);
if (fe0->dvb.frontend != NULL) {
if (!dvb_attach(stb6100_attach,
fe0->dvb.frontend,
&prof_8000_stb6100_config,
&i2c_bus->i2c_adap))
goto frontend_detach;
if (fe0->dvb.frontend == NULL)
break;
if (!dvb_attach(stb6100_attach,
fe0->dvb.frontend,
&prof_8000_stb6100_config,
&i2c_bus->i2c_adap))
goto frontend_detach;
fe0->dvb.frontend->ops.set_voltage = p8000_set_voltage;
}
fe0->dvb.frontend->ops.set_voltage = p8000_set_voltage;
break;
case CX23885_BOARD_HAUPPAUGE_HVR4400:
i2c_bus = &dev->i2c_bus[0];
@ -1563,30 +1687,31 @@ static int dvb_register(struct cx23885_tsport *port)
fe0->dvb.frontend = dvb_attach(tda10071_attach,
&hauppauge_tda10071_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
if (!dvb_attach(a8293_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_a8293_config))
goto frontend_detach;
}
if (fe0->dvb.frontend == NULL)
break;
if (!dvb_attach(a8293_attach, fe0->dvb.frontend,
&i2c_bus->i2c_adap,
&hauppauge_a8293_config))
goto frontend_detach;
break;
/* port c */
case 2:
fe0->dvb.frontend = dvb_attach(si2165_attach,
&hauppauge_hvr4400_si2165_config,
&i2c_bus->i2c_adap);
if (fe0->dvb.frontend != NULL) {
fe0->dvb.frontend->ops.i2c_gate_ctrl = NULL;
if (!dvb_attach(tda18271_attach,
fe0->dvb.frontend,
0x60, &i2c_bus2->i2c_adap,
&hauppauge_hvr4400_tuner_config))
goto frontend_detach;
}
if (fe0->dvb.frontend == NULL)
break;
fe0->dvb.frontend->ops.i2c_gate_ctrl = NULL;
if (!dvb_attach(tda18271_attach,
fe0->dvb.frontend,
0x60, &i2c_bus2->i2c_adap,
&hauppauge_hvr4400_tuner_config))
goto frontend_detach;
break;
}
break;
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_S950:
i2c_bus = &dev->i2c_bus[0];
i2c_bus2 = &dev->i2c_bus[1];
switch (port->nr) {
@ -1680,6 +1805,201 @@ static int dvb_register(struct cx23885_tsport *port)
break;
}
break;
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_TT_CT2_4500_CI:
i2c_bus = &dev->i2c_bus[1];
i2c_bus2 = &dev->i2c_bus[0];
/* attach frontend */
memset(&si2168_config, 0, sizeof(si2168_config));
si2168_config.i2c_adapter = &adapter;
si2168_config.fe = &fe0->dvb.frontend;
si2168_config.ts_mode = SI2168_TS_PARALLEL;
memset(&info, 0, sizeof(struct i2c_board_info));
strlcpy(info.type, "si2168", I2C_NAME_SIZE);
info.addr = 0x64;
info.platform_data = &si2168_config;
request_module(info.type);
client_demod = i2c_new_device(&i2c_bus->i2c_adap, &info);
if (client_demod == NULL ||
client_demod->dev.driver == NULL)
goto frontend_detach;
if (!try_module_get(client_demod->dev.driver->owner)) {
i2c_unregister_device(client_demod);
goto frontend_detach;
}
port->i2c_client_demod = client_demod;
/* attach tuner */
memset(&si2157_config, 0, sizeof(si2157_config));
si2157_config.fe = fe0->dvb.frontend;
memset(&info, 0, sizeof(struct i2c_board_info));
strlcpy(info.type, "si2157", I2C_NAME_SIZE);
info.addr = 0x60;
info.platform_data = &si2157_config;
request_module(info.type);
client_tuner = i2c_new_device(adapter, &info);
if (client_tuner == NULL ||
client_tuner->dev.driver == NULL) {
module_put(client_demod->dev.driver->owner);
i2c_unregister_device(client_demod);
goto frontend_detach;
}
if (!try_module_get(client_tuner->dev.driver->owner)) {
i2c_unregister_device(client_tuner);
module_put(client_demod->dev.driver->owner);
i2c_unregister_device(client_demod);
goto frontend_detach;
}
port->i2c_client_tuner = client_tuner;
break;
case CX23885_BOARD_DVBSKY_S950C:
i2c_bus = &dev->i2c_bus[1];
i2c_bus2 = &dev->i2c_bus[0];
/* attach frontend */
fe0->dvb.frontend = dvb_attach(m88ds3103_attach,
&dvbsky_s950c_m88ds3103_config,
&i2c_bus->i2c_adap, &adapter);
if (fe0->dvb.frontend == NULL)
break;
/* attach tuner */
memset(&m88ts2022_config, 0, sizeof(m88ts2022_config));
m88ts2022_config.fe = fe0->dvb.frontend;
m88ts2022_config.clock = 27000000;
memset(&info, 0, sizeof(struct i2c_board_info));
strlcpy(info.type, "m88ts2022", I2C_NAME_SIZE);
info.addr = 0x60;
info.platform_data = &m88ts2022_config;
request_module(info.type);
client_tuner = i2c_new_device(adapter, &info);
if (client_tuner == NULL ||
client_tuner->dev.driver == NULL)
goto frontend_detach;
if (!try_module_get(client_tuner->dev.driver->owner)) {
i2c_unregister_device(client_tuner);
goto frontend_detach;
}
/* delegate signal strength measurement to tuner */
fe0->dvb.frontend->ops.read_signal_strength =
fe0->dvb.frontend->ops.tuner_ops.get_rf_strength;
port->i2c_client_tuner = client_tuner;
break;
case CX23885_BOARD_DVBSKY_S952:
switch (port->nr) {
/* port b */
case 1:
i2c_bus = &dev->i2c_bus[1];
p_m88ds3103_config = &dvbsky_t9580_m88ds3103_config;
p_set_voltage = dvbsky_t9580_set_voltage;
break;
/* port c */
case 2:
i2c_bus = &dev->i2c_bus[0];
p_m88ds3103_config = &dvbsky_s952_portc_m88ds3103_config;
p_set_voltage = dvbsky_s952_portc_set_voltage;
break;
}
/* attach frontend */
fe0->dvb.frontend = dvb_attach(m88ds3103_attach,
p_m88ds3103_config,
&i2c_bus->i2c_adap, &adapter);
if (fe0->dvb.frontend == NULL)
break;
/* attach tuner */
memset(&m88ts2022_config, 0, sizeof(m88ts2022_config));
m88ts2022_config.fe = fe0->dvb.frontend;
m88ts2022_config.clock = 27000000;
memset(&info, 0, sizeof(struct i2c_board_info));
strlcpy(info.type, "m88ts2022", I2C_NAME_SIZE);
info.addr = 0x60;
info.platform_data = &m88ts2022_config;
request_module(info.type);
client_tuner = i2c_new_device(adapter, &info);
if (client_tuner == NULL ||
client_tuner->dev.driver == NULL)
goto frontend_detach;
if (!try_module_get(client_tuner->dev.driver->owner)) {
i2c_unregister_device(client_tuner);
goto frontend_detach;
}
/* delegate signal strength measurement to tuner */
fe0->dvb.frontend->ops.read_signal_strength =
fe0->dvb.frontend->ops.tuner_ops.get_rf_strength;
/*
* for setting the voltage we need to set GPIOs on
* the card.
*/
port->fe_set_voltage =
fe0->dvb.frontend->ops.set_voltage;
fe0->dvb.frontend->ops.set_voltage = p_set_voltage;
port->i2c_client_tuner = client_tuner;
break;
case CX23885_BOARD_DVBSKY_T982:
memset(&si2168_config, 0, sizeof(si2168_config));
switch (port->nr) {
/* port b */
case 1:
i2c_bus = &dev->i2c_bus[1];
si2168_config.ts_mode = SI2168_TS_PARALLEL;
break;
/* port c */
case 2:
i2c_bus = &dev->i2c_bus[0];
si2168_config.ts_mode = SI2168_TS_SERIAL;
break;
}
/* attach frontend */
si2168_config.i2c_adapter = &adapter;
si2168_config.fe = &fe0->dvb.frontend;
memset(&info, 0, sizeof(struct i2c_board_info));
strlcpy(info.type, "si2168", I2C_NAME_SIZE);
info.addr = 0x64;
info.platform_data = &si2168_config;
request_module(info.type);
client_demod = i2c_new_device(&i2c_bus->i2c_adap, &info);
if (client_demod == NULL ||
client_demod->dev.driver == NULL)
goto frontend_detach;
if (!try_module_get(client_demod->dev.driver->owner)) {
i2c_unregister_device(client_demod);
goto frontend_detach;
}
port->i2c_client_demod = client_demod;
/* attach tuner */
memset(&si2157_config, 0, sizeof(si2157_config));
si2157_config.fe = fe0->dvb.frontend;
memset(&info, 0, sizeof(struct i2c_board_info));
strlcpy(info.type, "si2157", I2C_NAME_SIZE);
info.addr = 0x60;
info.platform_data = &si2157_config;
request_module(info.type);
client_tuner = i2c_new_device(adapter, &info);
if (client_tuner == NULL ||
client_tuner->dev.driver == NULL) {
module_put(client_demod->dev.driver->owner);
i2c_unregister_device(client_demod);
goto frontend_detach;
}
if (!try_module_get(client_tuner->dev.driver->owner)) {
i2c_unregister_device(client_tuner);
module_put(client_demod->dev.driver->owner);
i2c_unregister_device(client_demod);
port->i2c_client_demod = NULL;
goto frontend_detach;
}
port->i2c_client_tuner = client_tuner;
break;
default:
printk(KERN_INFO "%s: The frontend of your DVB/ATSC card "
" isn't supported yet\n",
@ -1754,7 +2074,10 @@ static int dvb_register(struct cx23885_tsport *port)
memcpy(port->frontends.adapter.proposed_mac, eeprom + 0xa0, 6);
break;
}
case CX23885_BOARD_DVBSKY_T9580: {
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982: {
u8 eeprom[256]; /* 24C02 i2c eeprom */
if (port->nr > 2)
@ -1764,12 +2087,67 @@ static int dvb_register(struct cx23885_tsport *port)
dev->i2c_bus[0].i2c_client.addr = 0xa0 >> 1;
tveeprom_read(&dev->i2c_bus[0].i2c_client, eeprom,
sizeof(eeprom));
printk(KERN_INFO "DVBSky T9580 port %d MAC address: %pM\n",
port->nr, eeprom + 0xc0 + (port->nr-1) * 8);
printk(KERN_INFO "%s port %d MAC address: %pM\n",
cx23885_boards[dev->board].name, port->nr,
eeprom + 0xc0 + (port->nr-1) * 8);
memcpy(port->frontends.adapter.proposed_mac, eeprom + 0xc0 +
(port->nr-1) * 8, 6);
break;
}
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_TT_CT2_4500_CI: {
u8 eeprom[256]; /* 24C02 i2c eeprom */
/* attach CI */
memset(&sp2_config, 0, sizeof(sp2_config));
sp2_config.dvb_adap = &port->frontends.adapter;
sp2_config.priv = port;
sp2_config.ci_control = cx23885_sp2_ci_ctrl;
memset(&info, 0, sizeof(struct i2c_board_info));
strlcpy(info.type, "sp2", I2C_NAME_SIZE);
info.addr = 0x40;
info.platform_data = &sp2_config;
request_module(info.type);
client_ci = i2c_new_device(&i2c_bus2->i2c_adap, &info);
if (client_ci == NULL ||
client_ci->dev.driver == NULL) {
if (client_tuner) {
module_put(client_tuner->dev.driver->owner);
i2c_unregister_device(client_tuner);
}
if (client_demod) {
module_put(client_demod->dev.driver->owner);
i2c_unregister_device(client_demod);
}
goto frontend_detach;
}
if (!try_module_get(client_ci->dev.driver->owner)) {
i2c_unregister_device(client_ci);
if (client_tuner) {
module_put(client_tuner->dev.driver->owner);
i2c_unregister_device(client_tuner);
}
if (client_demod) {
module_put(client_demod->dev.driver->owner);
i2c_unregister_device(client_demod);
}
goto frontend_detach;
}
port->i2c_client_ci = client_ci;
if (port->nr != 1)
break;
/* Read entire EEPROM */
dev->i2c_bus[0].i2c_client.addr = 0xa0 >> 1;
tveeprom_read(&dev->i2c_bus[0].i2c_client, eeprom,
sizeof(eeprom));
printk(KERN_INFO "%s MAC address: %pM\n",
cx23885_boards[dev->board].name, eeprom + 0xc0);
memcpy(port->frontends.adapter.proposed_mac, eeprom + 0xc0, 6);
break;
}
}
return ret;
@ -1810,7 +2188,7 @@ int cx23885_dvb_register(struct cx23885_tsport *port)
fe0 = vb2_dvb_get_frontend(&port->frontends, i);
if (!fe0)
err = -EINVAL;
return -EINVAL;
dprintk(1, "%s\n", __func__);
dprintk(1, " ->probed by Card=%d Name=%s, PCI %02x:%02x\n",
@ -1853,6 +2231,13 @@ int cx23885_dvb_unregister(struct cx23885_tsport *port)
struct vb2_dvb_frontend *fe0;
struct i2c_client *client;
/* remove I2C client for CI */
client = port->i2c_client_ci;
if (client) {
module_put(client->dev.driver->owner);
i2c_unregister_device(client);
}
/* remove I2C client for tuner */
client = port->i2c_client_tuner;
if (client) {

View file

@ -87,6 +87,13 @@ void cx23885_input_rx_work_handler(struct cx23885_dev *dev, u32 events)
case CX23885_BOARD_MYGICA_X8507:
case CX23885_BOARD_TBS_6980:
case CX23885_BOARD_TBS_6981:
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
/*
* The only boards we handle right now. However other boards
* using the CX2388x integrated IR controller should be similar
@ -139,6 +146,13 @@ static int cx23885_input_ir_start(struct cx23885_dev *dev)
case CX23885_BOARD_HAUPPAUGE_HVR1290:
case CX23885_BOARD_HAUPPAUGE_HVR1250:
case CX23885_BOARD_MYGICA_X8507:
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_TT_CT2_4500_CI:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
/*
* The IR controller on this board only returns pulse widths.
* Any other mode setting will fail to set up the device.
@ -305,6 +319,23 @@ int cx23885_input_init(struct cx23885_dev *dev)
/* A guess at the remote */
rc_map = RC_MAP_TBS_NEC;
break;
case CX23885_BOARD_DVBSKY_T9580:
case CX23885_BOARD_DVBSKY_T980C:
case CX23885_BOARD_DVBSKY_S950C:
case CX23885_BOARD_DVBSKY_S950:
case CX23885_BOARD_DVBSKY_S952:
case CX23885_BOARD_DVBSKY_T982:
/* Integrated CX23885 IR controller */
driver_type = RC_DRIVER_IR_RAW;
allowed_protos = RC_BIT_ALL;
rc_map = RC_MAP_DVBSKY;
break;
case CX23885_BOARD_TT_CT2_4500_CI:
/* Integrated CX23885 IR controller */
driver_type = RC_DRIVER_IR_RAW;
allowed_protos = RC_BIT_ALL;
rc_map = RC_MAP_TT_1500;
break;
default:
return -ENODEV;
}

Some files were not shown because too many files have changed in this diff Show more