Merge branch 'topic/kbuild-fixes-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/linux-media

Pull media build fixes from Mauro Carvalho Chehab:
 "A series of patches that fix compilation on non-x86 archs.

  While most of them are just build fixes, there are some fixes for real
  bugs, as there are a number of drivers using dynamic stack allocation.
  A few of those might be considered a security risk, if the i2c-dev
  module is loaded, as someone could be sending very long I2C data that
  could potentially overflow the Kernel stack.  Ok, as using /dev/i2c-*
  devnodes usually requires root on usual distros, and exploiting it
  would require a DVB board or USB stick, the risk is not high"

* 'topic/kbuild-fixes-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/linux-media: (28 commits)
  [media] platform drivers: Fix build on frv arch
  [media] lirc_zilog: Don't use dynamic static allocation
  [media] mxl111sf: Don't use dynamic static allocation
  [media] af9035: Don't use dynamic static allocation
  [media] af9015: Don't use dynamic static allocation
  [media] dw2102: Don't use dynamic static allocation
  [media] dibusb-common: Don't use dynamic static allocation
  [media] cxusb: Don't use dynamic static allocation
  [media] v4l2-async: Don't use dynamic static allocation
  [media] cimax2: Don't use dynamic static allocation
  [media] tuner-xc2028: Don't use dynamic static allocation
  [media] tuners: Don't use dynamic static allocation
  [media] av7110_hw: Don't use dynamic static allocation
  [media] stv090x: Don't use dynamic static allocation
  [media] stv0367: Don't use dynamic static allocation
  [media] stb0899_drv: Don't use dynamic static allocation
  [media] dvb-frontends: Don't use dynamic static allocation
  [media] dvb-frontends: Don't use dynamic static allocation
  [media] s5h1420: Don't use dynamic static allocation
  [media] uvc/lirc_serial: Fix some warnings on parisc arch
  ...
This commit is contained in:
Linus Torvalds
2013-11-18 15:10:05 -08:00
47 changed files with 610 additions and 119 deletions

View File

@@ -24,6 +24,9 @@
#include "af9013_priv.h" #include "af9013_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
struct af9013_state { struct af9013_state {
struct i2c_adapter *i2c; struct i2c_adapter *i2c;
struct dvb_frontend fe; struct dvb_frontend fe;
@@ -50,16 +53,23 @@ static int af9013_wr_regs_i2c(struct af9013_state *priv, u8 mbox, u16 reg,
const u8 *val, int len) const u8 *val, int len)
{ {
int ret; int ret;
u8 buf[3+len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->config.i2c_addr, .addr = priv->config.i2c_addr,
.flags = 0, .flags = 0,
.len = sizeof(buf), .len = 3 + len,
.buf = buf, .buf = buf,
} }
}; };
if (3 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = (reg >> 8) & 0xff; buf[0] = (reg >> 8) & 0xff;
buf[1] = (reg >> 0) & 0xff; buf[1] = (reg >> 0) & 0xff;
buf[2] = mbox; buf[2] = mbox;

View File

@@ -21,6 +21,9 @@
#include "af9033_priv.h" #include "af9033_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
struct af9033_state { struct af9033_state {
struct i2c_adapter *i2c; struct i2c_adapter *i2c;
struct dvb_frontend fe; struct dvb_frontend fe;
@@ -40,16 +43,23 @@ static int af9033_wr_regs(struct af9033_state *state, u32 reg, const u8 *val,
int len) int len)
{ {
int ret; int ret;
u8 buf[3 + len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = state->cfg.i2c_addr, .addr = state->cfg.i2c_addr,
.flags = 0, .flags = 0,
.len = sizeof(buf), .len = 3 + len,
.buf = buf, .buf = buf,
} }
}; };
if (3 + len > sizeof(buf)) {
dev_warn(&state->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = (reg >> 16) & 0xff; buf[0] = (reg >> 16) & 0xff;
buf[1] = (reg >> 8) & 0xff; buf[1] = (reg >> 8) & 0xff;
buf[2] = (reg >> 0) & 0xff; buf[2] = (reg >> 0) & 0xff;
@@ -161,7 +171,14 @@ static int af9033_wr_reg_val_tab(struct af9033_state *state,
const struct reg_val *tab, int tab_len) const struct reg_val *tab, int tab_len)
{ {
int ret, i, j; int ret, i, j;
u8 buf[tab_len]; u8 buf[MAX_XFER_SIZE];
if (tab_len > sizeof(buf)) {
dev_warn(&state->i2c->dev,
"%s: i2c wr len=%d is too big!\n",
KBUILD_MODNAME, tab_len);
return -EINVAL;
}
dev_dbg(&state->i2c->dev, "%s: tab_len=%d\n", __func__, tab_len); dev_dbg(&state->i2c->dev, "%s: tab_len=%d\n", __func__, tab_len);

View File

@@ -44,6 +44,9 @@
#include "bcm3510.h" #include "bcm3510.h"
#include "bcm3510_priv.h" #include "bcm3510_priv.h"
/* Max transfer size done by bcm3510_do_hab_cmd() function */
#define MAX_XFER_SIZE 128
struct bcm3510_state { struct bcm3510_state {
struct i2c_adapter* i2c; struct i2c_adapter* i2c;
@@ -201,9 +204,19 @@ static int bcm3510_hab_send_request(struct bcm3510_state *st, u8 *buf, int len)
static int bcm3510_do_hab_cmd(struct bcm3510_state *st, u8 cmd, u8 msgid, u8 *obuf, u8 olen, u8 *ibuf, u8 ilen) static int bcm3510_do_hab_cmd(struct bcm3510_state *st, u8 cmd, u8 msgid, u8 *obuf, u8 olen, u8 *ibuf, u8 ilen)
{ {
u8 ob[olen+2],ib[ilen+2]; u8 ob[MAX_XFER_SIZE], ib[MAX_XFER_SIZE];
int ret = 0; int ret = 0;
if (ilen + 2 > sizeof(ib)) {
deb_hab("do_hab_cmd: ilen=%d is too big!\n", ilen);
return -EINVAL;
}
if (olen + 2 > sizeof(ob)) {
deb_hab("do_hab_cmd: olen=%d is too big!\n", olen);
return -EINVAL;
}
ob[0] = cmd; ob[0] = cmd;
ob[1] = msgid; ob[1] = msgid;
memcpy(&ob[2],obuf,olen); memcpy(&ob[2],obuf,olen);

View File

@@ -21,12 +21,15 @@
#include "cxd2820r_priv.h" #include "cxd2820r_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
/* write multiple registers */ /* write multiple registers */
static int cxd2820r_wr_regs_i2c(struct cxd2820r_priv *priv, u8 i2c, u8 reg, static int cxd2820r_wr_regs_i2c(struct cxd2820r_priv *priv, u8 i2c, u8 reg,
u8 *val, int len) u8 *val, int len)
{ {
int ret; int ret;
u8 buf[len+1]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = i2c, .addr = i2c,
@@ -36,6 +39,13 @@ static int cxd2820r_wr_regs_i2c(struct cxd2820r_priv *priv, u8 i2c, u8 reg,
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], val, len); memcpy(&buf[1], val, len);
@@ -55,7 +65,7 @@ static int cxd2820r_rd_regs_i2c(struct cxd2820r_priv *priv, u8 i2c, u8 reg,
u8 *val, int len) u8 *val, int len)
{ {
int ret; int ret;
u8 buf[len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[2] = { struct i2c_msg msg[2] = {
{ {
.addr = i2c, .addr = i2c,
@@ -70,6 +80,13 @@ static int cxd2820r_rd_regs_i2c(struct cxd2820r_priv *priv, u8 i2c, u8 reg,
} }
}; };
if (len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
ret = i2c_transfer(priv->i2c, msg, 2); ret = i2c_transfer(priv->i2c, msg, 2);
if (ret == 2) { if (ret == 2) {
memcpy(val, buf, len); memcpy(val, buf, len);

View File

@@ -31,6 +31,9 @@
#include "itd1000.h" #include "itd1000.h"
#include "itd1000_priv.h" #include "itd1000_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static int debug; static int debug;
module_param(debug, int, 0644); module_param(debug, int, 0644);
MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off)."); MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
@@ -52,10 +55,18 @@ MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
/* don't write more than one byte with flexcop behind */ /* don't write more than one byte with flexcop behind */
static int itd1000_write_regs(struct itd1000_state *state, u8 reg, u8 v[], u8 len) static int itd1000_write_regs(struct itd1000_state *state, u8 reg, u8 v[], u8 len)
{ {
u8 buf[1+len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg = { struct i2c_msg msg = {
.addr = state->cfg->i2c_address, .flags = 0, .buf = buf, .len = len+1 .addr = state->cfg->i2c_address, .flags = 0, .buf = buf, .len = len+1
}; };
if (1 + len > sizeof(buf)) {
printk(KERN_WARNING
"itd1000: i2c wr reg=%04x: len=%d is too big!\n",
reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], v, len); memcpy(&buf[1], v, len);

View File

@@ -36,6 +36,8 @@
#include "mt312_priv.h" #include "mt312_priv.h"
#include "mt312.h" #include "mt312.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
struct mt312_state { struct mt312_state {
struct i2c_adapter *i2c; struct i2c_adapter *i2c;
@@ -96,9 +98,15 @@ static int mt312_write(struct mt312_state *state, const enum mt312_reg_addr reg,
const u8 *src, const size_t count) const u8 *src, const size_t count)
{ {
int ret; int ret;
u8 buf[count + 1]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg; struct i2c_msg msg;
if (1 + count > sizeof(buf)) {
printk(KERN_WARNING
"mt312: write: len=%zd is too big!\n", count);
return -EINVAL;
}
if (debug) { if (debug) {
int i; int i;
dprintk("W(%d):", reg & 0x7f); dprintk("W(%d):", reg & 0x7f);

View File

@@ -39,6 +39,9 @@
*/ */
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
#define NXT2002_DEFAULT_FIRMWARE "dvb-fe-nxt2002.fw" #define NXT2002_DEFAULT_FIRMWARE "dvb-fe-nxt2002.fw"
#define NXT2004_DEFAULT_FIRMWARE "dvb-fe-nxt2004.fw" #define NXT2004_DEFAULT_FIRMWARE "dvb-fe-nxt2004.fw"
#define CRC_CCIT_MASK 0x1021 #define CRC_CCIT_MASK 0x1021
@@ -95,10 +98,16 @@ static int i2c_readbytes(struct nxt200x_state *state, u8 addr, u8 *buf, u8 len)
static int nxt200x_writebytes (struct nxt200x_state* state, u8 reg, static int nxt200x_writebytes (struct nxt200x_state* state, u8 reg,
const u8 *buf, u8 len) const u8 *buf, u8 len)
{ {
u8 buf2 [len+1]; u8 buf2[MAX_XFER_SIZE];
int err; int err;
struct i2c_msg msg = { .addr = state->config->demod_address, .flags = 0, .buf = buf2, .len = len + 1 }; struct i2c_msg msg = { .addr = state->config->demod_address, .flags = 0, .buf = buf2, .len = len + 1 };
if (1 + len > sizeof(buf2)) {
pr_warn("%s: i2c wr reg=%04x: len=%d is too big!\n",
__func__, reg, len);
return -EINVAL;
}
buf2[0] = reg; buf2[0] = reg;
memcpy(&buf2[1], buf, len); memcpy(&buf2[1], buf, len);

View File

@@ -27,20 +27,30 @@
#include "rtl2830_priv.h" #include "rtl2830_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
/* write multiple hardware registers */ /* write multiple hardware registers */
static int rtl2830_wr(struct rtl2830_priv *priv, u8 reg, const u8 *val, int len) static int rtl2830_wr(struct rtl2830_priv *priv, u8 reg, const u8 *val, int len)
{ {
int ret; int ret;
u8 buf[1+len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->cfg.i2c_addr, .addr = priv->cfg.i2c_addr,
.flags = 0, .flags = 0,
.len = 1+len, .len = 1 + len,
.buf = buf, .buf = buf,
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], val, len); memcpy(&buf[1], val, len);

View File

@@ -22,6 +22,9 @@
#include "dvb_math.h" #include "dvb_math.h"
#include <linux/bitops.h> #include <linux/bitops.h>
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
int rtl2832_debug; int rtl2832_debug;
module_param_named(debug, rtl2832_debug, int, 0644); module_param_named(debug, rtl2832_debug, int, 0644);
MODULE_PARM_DESC(debug, "Turn on/off frontend debugging (default:off)."); MODULE_PARM_DESC(debug, "Turn on/off frontend debugging (default:off).");
@@ -162,16 +165,23 @@ static const struct rtl2832_reg_entry registers[] = {
static int rtl2832_wr(struct rtl2832_priv *priv, u8 reg, u8 *val, int len) static int rtl2832_wr(struct rtl2832_priv *priv, u8 reg, u8 *val, int len)
{ {
int ret; int ret;
u8 buf[1+len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->cfg.i2c_addr, .addr = priv->cfg.i2c_addr,
.flags = 0, .flags = 0,
.len = 1+len, .len = 1 + len,
.buf = buf, .buf = buf,
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], val, len); memcpy(&buf[1], val, len);

View File

@@ -836,9 +836,16 @@ static u32 s5h1420_tuner_i2c_func(struct i2c_adapter *adapter)
static int s5h1420_tuner_i2c_tuner_xfer(struct i2c_adapter *i2c_adap, struct i2c_msg msg[], int num) static int s5h1420_tuner_i2c_tuner_xfer(struct i2c_adapter *i2c_adap, struct i2c_msg msg[], int num)
{ {
struct s5h1420_state *state = i2c_get_adapdata(i2c_adap); struct s5h1420_state *state = i2c_get_adapdata(i2c_adap);
struct i2c_msg m[1 + num]; struct i2c_msg m[3];
u8 tx_open[2] = { CON_1, state->CON_1_val | 1 }; /* repeater stops once there was a stop condition */ u8 tx_open[2] = { CON_1, state->CON_1_val | 1 }; /* repeater stops once there was a stop condition */
if (1 + num > ARRAY_SIZE(m)) {
printk(KERN_WARNING
"%s: i2c xfer: num=%d is too big!\n",
KBUILD_MODNAME, num);
return -EOPNOTSUPP;
}
memset(m, 0, sizeof(struct i2c_msg) * (1 + num)); memset(m, 0, sizeof(struct i2c_msg) * (1 + num));
m[0].addr = state->config->demod_address; m[0].addr = state->config->demod_address;
@@ -847,7 +854,7 @@ static int s5h1420_tuner_i2c_tuner_xfer(struct i2c_adapter *i2c_adap, struct i2c
memcpy(&m[1], msg, sizeof(struct i2c_msg) * num); memcpy(&m[1], msg, sizeof(struct i2c_msg) * num);
return i2c_transfer(state->i2c, m, 1+num) == 1 + num ? num : -EIO; return i2c_transfer(state->i2c, m, 1 + num) == 1 + num ? num : -EIO;
} }
static struct i2c_algorithm s5h1420_tuner_i2c_algo = { static struct i2c_algorithm s5h1420_tuner_i2c_algo = {

View File

@@ -32,6 +32,9 @@
#include "stb0899_priv.h" #include "stb0899_priv.h"
#include "stb0899_reg.h" #include "stb0899_reg.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static unsigned int verbose = 0;//1; static unsigned int verbose = 0;//1;
module_param(verbose, int, 0644); module_param(verbose, int, 0644);
@@ -499,7 +502,7 @@ err:
int stb0899_write_regs(struct stb0899_state *state, unsigned int reg, u8 *data, u32 count) int stb0899_write_regs(struct stb0899_state *state, unsigned int reg, u8 *data, u32 count)
{ {
int ret; int ret;
u8 buf[2 + count]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg i2c_msg = { struct i2c_msg i2c_msg = {
.addr = state->config->demod_address, .addr = state->config->demod_address,
.flags = 0, .flags = 0,
@@ -507,6 +510,13 @@ int stb0899_write_regs(struct stb0899_state *state, unsigned int reg, u8 *data,
.len = 2 + count .len = 2 + count
}; };
if (2 + count > sizeof(buf)) {
printk(KERN_WARNING
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, count);
return -EINVAL;
}
buf[0] = reg >> 8; buf[0] = reg >> 8;
buf[1] = reg & 0xff; buf[1] = reg & 0xff;
memcpy(&buf[2], data, count); memcpy(&buf[2], data, count);

View File

@@ -31,6 +31,8 @@
static unsigned int verbose; static unsigned int verbose;
module_param(verbose, int, 0644); module_param(verbose, int, 0644);
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
#define FE_ERROR 0 #define FE_ERROR 0
#define FE_NOTICE 1 #define FE_NOTICE 1
@@ -183,7 +185,7 @@ static int stb6100_read_reg(struct stb6100_state *state, u8 reg)
static int stb6100_write_reg_range(struct stb6100_state *state, u8 buf[], int start, int len) static int stb6100_write_reg_range(struct stb6100_state *state, u8 buf[], int start, int len)
{ {
int rc; int rc;
u8 cmdbuf[len + 1]; u8 cmdbuf[MAX_XFER_SIZE];
struct i2c_msg msg = { struct i2c_msg msg = {
.addr = state->config->tuner_address, .addr = state->config->tuner_address,
.flags = 0, .flags = 0,
@@ -191,6 +193,13 @@ static int stb6100_write_reg_range(struct stb6100_state *state, u8 buf[], int st
.len = len + 1 .len = len + 1
}; };
if (1 + len > sizeof(buf)) {
printk(KERN_WARNING
"%s: i2c wr: len=%d is too big!\n",
KBUILD_MODNAME, len);
return -EINVAL;
}
if (unlikely(start < 1 || start + len > STB6100_NUMREGS)) { if (unlikely(start < 1 || start + len > STB6100_NUMREGS)) {
dprintk(verbose, FE_ERROR, 1, "Invalid register range %d:%d", dprintk(verbose, FE_ERROR, 1, "Invalid register range %d:%d",
start, len); start, len);

View File

@@ -33,6 +33,9 @@
#include "stv0367_regs.h" #include "stv0367_regs.h"
#include "stv0367_priv.h" #include "stv0367_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static int stvdebug; static int stvdebug;
module_param_named(debug, stvdebug, int, 0644); module_param_named(debug, stvdebug, int, 0644);
@@ -767,7 +770,7 @@ static struct st_register def0367cab[STV0367CAB_NBREGS] = {
static static
int stv0367_writeregs(struct stv0367_state *state, u16 reg, u8 *data, int len) int stv0367_writeregs(struct stv0367_state *state, u16 reg, u8 *data, int len)
{ {
u8 buf[len + 2]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg = { struct i2c_msg msg = {
.addr = state->config->demod_address, .addr = state->config->demod_address,
.flags = 0, .flags = 0,
@@ -776,6 +779,14 @@ int stv0367_writeregs(struct stv0367_state *state, u16 reg, u8 *data, int len)
}; };
int ret; int ret;
if (2 + len > sizeof(buf)) {
printk(KERN_WARNING
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = MSB(reg); buf[0] = MSB(reg);
buf[1] = LSB(reg); buf[1] = LSB(reg);
memcpy(buf + 2, data, len); memcpy(buf + 2, data, len);

View File

@@ -35,6 +35,9 @@
#include "stv090x.h" #include "stv090x.h"
#include "stv090x_priv.h" #include "stv090x_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static unsigned int verbose; static unsigned int verbose;
module_param(verbose, int, 0644); module_param(verbose, int, 0644);
@@ -722,9 +725,16 @@ static int stv090x_write_regs(struct stv090x_state *state, unsigned int reg, u8
{ {
const struct stv090x_config *config = state->config; const struct stv090x_config *config = state->config;
int ret; int ret;
u8 buf[2 + count]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg i2c_msg = { .addr = config->address, .flags = 0, .buf = buf, .len = 2 + count }; struct i2c_msg i2c_msg = { .addr = config->address, .flags = 0, .buf = buf, .len = 2 + count };
if (2 + count > sizeof(buf)) {
printk(KERN_WARNING
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, count);
return -EINVAL;
}
buf[0] = reg >> 8; buf[0] = reg >> 8;
buf[1] = reg & 0xff; buf[1] = reg & 0xff;
memcpy(&buf[2], data, count); memcpy(&buf[2], data, count);

View File

@@ -30,6 +30,9 @@
#include "stv6110.h" #include "stv6110.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static int debug; static int debug;
struct stv6110_priv { struct stv6110_priv {
@@ -68,7 +71,7 @@ static int stv6110_write_regs(struct dvb_frontend *fe, u8 buf[],
{ {
struct stv6110_priv *priv = fe->tuner_priv; struct stv6110_priv *priv = fe->tuner_priv;
int rc; int rc;
u8 cmdbuf[len + 1]; u8 cmdbuf[MAX_XFER_SIZE];
struct i2c_msg msg = { struct i2c_msg msg = {
.addr = priv->i2c_address, .addr = priv->i2c_address,
.flags = 0, .flags = 0,
@@ -78,6 +81,13 @@ static int stv6110_write_regs(struct dvb_frontend *fe, u8 buf[],
dprintk("%s\n", __func__); dprintk("%s\n", __func__);
if (1 + len > sizeof(cmdbuf)) {
printk(KERN_WARNING
"%s: i2c wr: len=%d is too big!\n",
KBUILD_MODNAME, len);
return -EINVAL;
}
if (start + len > 8) if (start + len > 8)
return -EINVAL; return -EINVAL;

View File

@@ -32,6 +32,9 @@
#include "stv6110x.h" #include "stv6110x.h"
#include "stv6110x_priv.h" #include "stv6110x_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static unsigned int verbose; static unsigned int verbose;
module_param(verbose, int, 0644); module_param(verbose, int, 0644);
MODULE_PARM_DESC(verbose, "Set Verbosity level"); MODULE_PARM_DESC(verbose, "Set Verbosity level");
@@ -61,7 +64,8 @@ static int stv6110x_write_regs(struct stv6110x_state *stv6110x, int start, u8 da
{ {
int ret; int ret;
const struct stv6110x_config *config = stv6110x->config; const struct stv6110x_config *config = stv6110x->config;
u8 buf[len + 1]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg = { struct i2c_msg msg = {
.addr = config->addr, .addr = config->addr,
.flags = 0, .flags = 0,
@@ -69,6 +73,13 @@ static int stv6110x_write_regs(struct stv6110x_state *stv6110x, int start, u8 da
.len = len + 1 .len = len + 1
}; };
if (1 + len > sizeof(buf)) {
printk(KERN_WARNING
"%s: i2c wr: len=%d is too big!\n",
KBUILD_MODNAME, len);
return -EINVAL;
}
if (start + len > 8) if (start + len > 8)
return -EINVAL; return -EINVAL;

View File

@@ -20,6 +20,9 @@
#include "tda10071_priv.h" #include "tda10071_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static struct dvb_frontend_ops tda10071_ops; static struct dvb_frontend_ops tda10071_ops;
/* write multiple registers */ /* write multiple registers */
@@ -27,16 +30,23 @@ static int tda10071_wr_regs(struct tda10071_priv *priv, u8 reg, u8 *val,
int len) int len)
{ {
int ret; int ret;
u8 buf[len+1]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->cfg.demod_i2c_addr, .addr = priv->cfg.demod_i2c_addr,
.flags = 0, .flags = 0,
.len = sizeof(buf), .len = 1 + len,
.buf = buf, .buf = buf,
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], val, len); memcpy(&buf[1], val, len);
@@ -56,7 +66,7 @@ static int tda10071_rd_regs(struct tda10071_priv *priv, u8 reg, u8 *val,
int len) int len)
{ {
int ret; int ret;
u8 buf[len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[2] = { struct i2c_msg msg[2] = {
{ {
.addr = priv->cfg.demod_i2c_addr, .addr = priv->cfg.demod_i2c_addr,
@@ -66,11 +76,18 @@ static int tda10071_rd_regs(struct tda10071_priv *priv, u8 reg, u8 *val,
}, { }, {
.addr = priv->cfg.demod_i2c_addr, .addr = priv->cfg.demod_i2c_addr,
.flags = I2C_M_RD, .flags = I2C_M_RD,
.len = sizeof(buf), .len = len,
.buf = buf, .buf = buf,
} }
}; };
if (len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
ret = i2c_transfer(priv->i2c, msg, 2); ret = i2c_transfer(priv->i2c, msg, 2);
if (ret == 2) { if (ret == 2) {
memcpy(val, buf, len); memcpy(val, buf, len);

View File

@@ -34,6 +34,9 @@
#include "dvb_frontend.h" #include "dvb_frontend.h"
#include "tda18271c2dd.h" #include "tda18271c2dd.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
struct SStandardParam { struct SStandardParam {
s32 m_IFFrequency; s32 m_IFFrequency;
u32 m_BandWidth; u32 m_BandWidth;
@@ -139,11 +142,18 @@ static int i2c_write(struct i2c_adapter *adap, u8 adr, u8 *data, int len)
static int WriteRegs(struct tda_state *state, static int WriteRegs(struct tda_state *state,
u8 SubAddr, u8 *Regs, u16 nRegs) u8 SubAddr, u8 *Regs, u16 nRegs)
{ {
u8 data[nRegs+1]; u8 data[MAX_XFER_SIZE];
if (1 + nRegs > sizeof(data)) {
printk(KERN_WARNING
"%s: i2c wr: len=%d is too big!\n",
KBUILD_MODNAME, nRegs);
return -EINVAL;
}
data[0] = SubAddr; data[0] = SubAddr;
memcpy(data + 1, Regs, nRegs); memcpy(data + 1, Regs, nRegs);
return i2c_write(state->i2c, state->adr, data, nRegs+1); return i2c_write(state->i2c, state->adr, data, nRegs + 1);
} }
static int WriteReg(struct tda_state *state, u8 SubAddr, u8 Reg) static int WriteReg(struct tda_state *state, u8 SubAddr, u8 Reg)

View File

@@ -30,6 +30,9 @@
static int debug; static int debug;
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
#define dprintk(args...) \ #define dprintk(args...) \
do { \ do { \
if (debug) \ if (debug) \
@@ -98,7 +101,7 @@ static int zl10039_write(struct zl10039_state *state,
const enum zl10039_reg_addr reg, const u8 *src, const enum zl10039_reg_addr reg, const u8 *src,
const size_t count) const size_t count)
{ {
u8 buf[count + 1]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg = { struct i2c_msg msg = {
.addr = state->i2c_addr, .addr = state->i2c_addr,
.flags = 0, .flags = 0,
@@ -106,6 +109,13 @@ static int zl10039_write(struct zl10039_state *state,
.len = count + 1, .len = count + 1,
}; };
if (1 + count > sizeof(buf)) {
printk(KERN_WARNING
"%s: i2c wr reg=%04x: len=%zd is too big!\n",
KBUILD_MODNAME, reg, count);
return -EINVAL;
}
dprintk("%s\n", __func__); dprintk("%s\n", __func__);
/* Write register address and data in one go */ /* Write register address and data in one go */
buf[0] = reg; buf[0] = reg;

View File

@@ -324,23 +324,24 @@ static void cx18_eeprom_dump(struct cx18 *cx, unsigned char *eedata, int len)
/* Hauppauge card? get values from tveeprom */ /* Hauppauge card? get values from tveeprom */
void cx18_read_eeprom(struct cx18 *cx, struct tveeprom *tv) void cx18_read_eeprom(struct cx18 *cx, struct tveeprom *tv)
{ {
struct i2c_client c; struct i2c_client *c;
u8 eedata[256]; u8 eedata[256];
memset(&c, 0, sizeof(c)); c = kzalloc(sizeof(*c), GFP_KERNEL);
strlcpy(c.name, "cx18 tveeprom tmp", sizeof(c.name));
c.adapter = &cx->i2c_adap[0]; strlcpy(c->name, "cx18 tveeprom tmp", sizeof(c->name));
c.addr = 0xA0 >> 1; c->adapter = &cx->i2c_adap[0];
c->addr = 0xa0 >> 1;
memset(tv, 0, sizeof(*tv)); memset(tv, 0, sizeof(*tv));
if (tveeprom_read(&c, eedata, sizeof(eedata))) if (tveeprom_read(c, eedata, sizeof(eedata)))
return; goto ret;
switch (cx->card->type) { switch (cx->card->type) {
case CX18_CARD_HVR_1600_ESMT: case CX18_CARD_HVR_1600_ESMT:
case CX18_CARD_HVR_1600_SAMSUNG: case CX18_CARD_HVR_1600_SAMSUNG:
case CX18_CARD_HVR_1600_S5H1411: case CX18_CARD_HVR_1600_S5H1411:
tveeprom_hauppauge_analog(&c, tv, eedata); tveeprom_hauppauge_analog(c, tv, eedata);
break; break;
case CX18_CARD_YUAN_MPC718: case CX18_CARD_YUAN_MPC718:
case CX18_CARD_GOTVIEW_PCI_DVD3: case CX18_CARD_GOTVIEW_PCI_DVD3:
@@ -354,6 +355,9 @@ void cx18_read_eeprom(struct cx18 *cx, struct tveeprom *tv)
cx18_eeprom_dump(cx, eedata, sizeof(eedata)); cx18_eeprom_dump(cx, eedata, sizeof(eedata));
break; break;
} }
ret:
kfree(c);
} }
static void cx18_process_eeprom(struct cx18 *cx) static void cx18_process_eeprom(struct cx18 *cx)

View File

@@ -26,6 +26,10 @@
#include "cx23885.h" #include "cx23885.h"
#include "cimax2.h" #include "cimax2.h"
#include "dvb_ca_en50221.h" #include "dvb_ca_en50221.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
/**** Bit definitions for MC417_RWD and MC417_OEN registers *** /**** Bit definitions for MC417_RWD and MC417_OEN registers ***
bits 31-16 bits 31-16
+-----------+ +-----------+
@@ -125,7 +129,7 @@ static int netup_write_i2c(struct i2c_adapter *i2c_adap, u8 addr, u8 reg,
u8 *buf, int len) u8 *buf, int len)
{ {
int ret; int ret;
u8 buffer[len + 1]; u8 buffer[MAX_XFER_SIZE];
struct i2c_msg msg = { struct i2c_msg msg = {
.addr = addr, .addr = addr,
@@ -134,6 +138,13 @@ static int netup_write_i2c(struct i2c_adapter *i2c_adap, u8 addr, u8 reg,
.len = len + 1 .len = len + 1
}; };
if (1 + len > sizeof(buffer)) {
printk(KERN_WARNING
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buffer[0] = reg; buffer[0] = reg;
memcpy(&buffer[1], buf, len); memcpy(&buffer[1], buf, len);

View File

@@ -22,7 +22,7 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
* Or, point your browser to http://www.gnu.org/copyleft/gpl.html * Or, point your browser to http://www.gnu.org/copyleft/gpl.html
* *
* the project's page is at http://www.linuxtv.org/ * the project's page is at http://www.linuxtv.org/
*/ */
/* for debugging ARM communication: */ /* for debugging ARM communication: */
@@ -40,6 +40,14 @@
#define _NOHANDSHAKE #define _NOHANDSHAKE
/*
* Max transfer size done by av7110_fw_cmd()
*
* The maximum size passed to this function is 6 bytes. The buffer also
* uses two additional ones for type and size. So, 8 bytes is enough.
*/
#define MAX_XFER_SIZE 8
/**************************************************************************** /****************************************************************************
* DEBI functions * DEBI functions
****************************************************************************/ ****************************************************************************/
@@ -488,11 +496,18 @@ static int av7110_send_fw_cmd(struct av7110 *av7110, u16* buf, int length)
int av7110_fw_cmd(struct av7110 *av7110, int type, int com, int num, ...) int av7110_fw_cmd(struct av7110 *av7110, int type, int com, int num, ...)
{ {
va_list args; va_list args;
u16 buf[num + 2]; u16 buf[MAX_XFER_SIZE];
int i, ret; int i, ret;
// dprintk(4, "%p\n", av7110); // dprintk(4, "%p\n", av7110);
if (2 + num > sizeof(buf)) {
printk(KERN_WARNING
"%s: %s len=%d is too big!\n",
KBUILD_MODNAME, __func__, num);
return -EINVAL;
}
buf[0] = ((type << 8) | com); buf[0] = ((type << 8) | com);
buf[1] = num; buf[1] = num;

View File

@@ -1,6 +1,7 @@
config VIDEO_ZORAN config VIDEO_ZORAN
tristate "Zoran ZR36057/36067 Video For Linux" tristate "Zoran ZR36057/36067 Video For Linux"
depends on PCI && I2C_ALGOBIT && VIDEO_V4L2 && VIRT_TO_BUS depends on PCI && I2C_ALGOBIT && VIDEO_V4L2 && VIRT_TO_BUS
depends on !ALPHA
help help
Say Y for support for MJPEG capture cards based on the Zoran Say Y for support for MJPEG capture cards based on the Zoran
36057/36067 PCI controller chipset. This includes the Iomega 36057/36067 PCI controller chipset. This includes the Iomega

View File

@@ -16,6 +16,7 @@
#include <linux/delay.h> #include <linux/delay.h>
#include <linux/interrupt.h> #include <linux/interrupt.h>
#include <linux/io.h>
#include <linux/kernel.h> #include <linux/kernel.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/platform_data/camera-rcar.h> #include <linux/platform_data/camera-rcar.h>

View File

@@ -271,6 +271,7 @@ static void shark_unregister_leds(struct shark_device *shark)
cancel_work_sync(&shark->led_work); cancel_work_sync(&shark->led_work);
} }
#ifdef CONFIG_PM
static void shark_resume_leds(struct shark_device *shark) static void shark_resume_leds(struct shark_device *shark)
{ {
if (test_bit(BLUE_IS_PULSE, &shark->brightness_new)) if (test_bit(BLUE_IS_PULSE, &shark->brightness_new))
@@ -280,6 +281,7 @@ static void shark_resume_leds(struct shark_device *shark)
set_bit(RED_LED, &shark->brightness_new); set_bit(RED_LED, &shark->brightness_new);
schedule_work(&shark->led_work); schedule_work(&shark->led_work);
} }
#endif
#else #else
static int shark_register_leds(struct shark_device *shark, struct device *dev) static int shark_register_leds(struct shark_device *shark, struct device *dev)
{ {

View File

@@ -237,6 +237,7 @@ static void shark_unregister_leds(struct shark_device *shark)
cancel_work_sync(&shark->led_work); cancel_work_sync(&shark->led_work);
} }
#ifdef CONFIG_PM
static void shark_resume_leds(struct shark_device *shark) static void shark_resume_leds(struct shark_device *shark)
{ {
int i; int i;
@@ -246,6 +247,7 @@ static void shark_resume_leds(struct shark_device *shark)
schedule_work(&shark->led_work); schedule_work(&shark->led_work);
} }
#endif
#else #else
static int shark_register_leds(struct shark_device *shark, struct device *dev) static int shark_register_leds(struct shark_device *shark, struct device *dev)
{ {

View File

@@ -463,7 +463,7 @@ static int si470x_i2c_remove(struct i2c_client *client)
} }
#ifdef CONFIG_PM #ifdef CONFIG_PM_SLEEP
/* /*
* si470x_i2c_suspend - suspend the device * si470x_i2c_suspend - suspend the device
*/ */
@@ -509,7 +509,7 @@ static struct i2c_driver si470x_i2c_driver = {
.driver = { .driver = {
.name = "si470x", .name = "si470x",
.owner = THIS_MODULE, .owner = THIS_MODULE,
#ifdef CONFIG_PM #ifdef CONFIG_PM_SLEEP
.pm = &si470x_i2c_pm, .pm = &si470x_i2c_pm,
#endif #endif
}, },

View File

@@ -48,15 +48,15 @@
#define WM_SUB_TEST 0xF #define WM_SUB_TEST 0xF
/* Different modes of the MSA register */ /* Different modes of the MSA register */
#define MODE_BUFFER 0x0 #define MSA_MODE_BUFFER 0x0
#define MODE_PRESET 0x1 #define MSA_MODE_PRESET 0x1
#define MODE_SEARCH 0x2 #define MSA_MODE_SEARCH 0x2
#define MODE_AF_UPDATE 0x3 #define MSA_MODE_AF_UPDATE 0x3
#define MODE_JUMP 0x4 #define MSA_MODE_JUMP 0x4
#define MODE_CHECK 0x5 #define MSA_MODE_CHECK 0x5
#define MODE_LOAD 0x6 #define MSA_MODE_LOAD 0x6
#define MODE_END 0x7 #define MSA_MODE_END 0x7
#define MODE_SHIFT 5 #define MSA_MODE_SHIFT 5
struct tef6862_state { struct tef6862_state {
struct v4l2_subdev sd; struct v4l2_subdev sd;
@@ -114,7 +114,7 @@ static int tef6862_s_frequency(struct v4l2_subdev *sd, const struct v4l2_frequen
clamp(freq, TEF6862_LO_FREQ, TEF6862_HI_FREQ); clamp(freq, TEF6862_LO_FREQ, TEF6862_HI_FREQ);
pll = 1964 + ((freq - TEF6862_LO_FREQ) * 20) / FREQ_MUL; pll = 1964 + ((freq - TEF6862_LO_FREQ) * 20) / FREQ_MUL;
i2cmsg[0] = (MODE_PRESET << MODE_SHIFT) | WM_SUB_PLLM; i2cmsg[0] = (MSA_MODE_PRESET << MSA_MODE_SHIFT) | WM_SUB_PLLM;
i2cmsg[1] = (pll >> 8) & 0xff; i2cmsg[1] = (pll >> 8) & 0xff;
i2cmsg[2] = pll & 0xff; i2cmsg[2] = pll & 0xff;

View File

@@ -76,8 +76,8 @@ struct fintek_dev {
} tx; } tx;
/* Config register index/data port pair */ /* Config register index/data port pair */
u8 cr_ip; u32 cr_ip;
u8 cr_dp; u32 cr_dp;
/* hardware I/O settings */ /* hardware I/O settings */
unsigned long cir_addr; unsigned long cir_addr;

View File

@@ -308,22 +308,12 @@ static int iguanair_set_tx_carrier(struct rc_dev *dev, uint32_t carrier)
cycles = DIV_ROUND_CLOSEST(24000000, carrier * 2) - cycles = DIV_ROUND_CLOSEST(24000000, carrier * 2) -
ir->cycle_overhead; ir->cycle_overhead;
/* make up the the remainer of 4-cycle blocks */ /*
switch (cycles & 3) { * Calculate minimum number of 7 cycles needed so
case 0: * we are left with a multiple of 4; so we want to have
sevens = 0; * (sevens * 7) & 3 == cycles & 3
break; */
case 1: sevens = (4 - cycles) & 3;
sevens = 3;
break;
case 2:
sevens = 2;
break;
case 3:
sevens = 1;
break;
}
fours = (cycles - sevens * 7) / 4; fours = (cycles - sevens * 7) / 4;
/* magic happens here */ /* magic happens here */

View File

@@ -84,8 +84,8 @@ struct nvt_dev {
} tx; } tx;
/* EFER Config register index/data pair */ /* EFER Config register index/data pair */
u8 cr_efir; u32 cr_efir;
u8 cr_efdr; u32 cr_efdr;
/* hardware I/O settings */ /* hardware I/O settings */
unsigned long cir_addr; unsigned long cir_addr;

View File

@@ -21,20 +21,30 @@
#include "e4000_priv.h" #include "e4000_priv.h"
#include <linux/math64.h> #include <linux/math64.h>
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
/* write multiple registers */ /* write multiple registers */
static int e4000_wr_regs(struct e4000_priv *priv, u8 reg, u8 *val, int len) static int e4000_wr_regs(struct e4000_priv *priv, u8 reg, u8 *val, int len)
{ {
int ret; int ret;
u8 buf[1 + len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->cfg->i2c_addr, .addr = priv->cfg->i2c_addr,
.flags = 0, .flags = 0,
.len = sizeof(buf), .len = 1 + len,
.buf = buf, .buf = buf,
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], val, len); memcpy(&buf[1], val, len);
@@ -54,7 +64,7 @@ static int e4000_wr_regs(struct e4000_priv *priv, u8 reg, u8 *val, int len)
static int e4000_rd_regs(struct e4000_priv *priv, u8 reg, u8 *val, int len) static int e4000_rd_regs(struct e4000_priv *priv, u8 reg, u8 *val, int len)
{ {
int ret; int ret;
u8 buf[len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[2] = { struct i2c_msg msg[2] = {
{ {
.addr = priv->cfg->i2c_addr, .addr = priv->cfg->i2c_addr,
@@ -64,11 +74,18 @@ static int e4000_rd_regs(struct e4000_priv *priv, u8 reg, u8 *val, int len)
}, { }, {
.addr = priv->cfg->i2c_addr, .addr = priv->cfg->i2c_addr,
.flags = I2C_M_RD, .flags = I2C_M_RD,
.len = sizeof(buf), .len = len,
.buf = buf, .buf = buf,
} }
}; };
if (len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c rd reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
ret = i2c_transfer(priv->i2c, msg, 2); ret = i2c_transfer(priv->i2c, msg, 2);
if (ret == 2) { if (ret == 2) {
memcpy(val, buf, len); memcpy(val, buf, len);

View File

@@ -20,6 +20,9 @@
#include "fc2580_priv.h" #include "fc2580_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
/* /*
* TODO: * TODO:
* I2C write and read works only for one single register. Multiple registers * I2C write and read works only for one single register. Multiple registers
@@ -41,16 +44,23 @@
static int fc2580_wr_regs(struct fc2580_priv *priv, u8 reg, u8 *val, int len) static int fc2580_wr_regs(struct fc2580_priv *priv, u8 reg, u8 *val, int len)
{ {
int ret; int ret;
u8 buf[1 + len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->cfg->i2c_addr, .addr = priv->cfg->i2c_addr,
.flags = 0, .flags = 0,
.len = sizeof(buf), .len = 1 + len,
.buf = buf, .buf = buf,
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], val, len); memcpy(&buf[1], val, len);
@@ -69,7 +79,7 @@ static int fc2580_wr_regs(struct fc2580_priv *priv, u8 reg, u8 *val, int len)
static int fc2580_rd_regs(struct fc2580_priv *priv, u8 reg, u8 *val, int len) static int fc2580_rd_regs(struct fc2580_priv *priv, u8 reg, u8 *val, int len)
{ {
int ret; int ret;
u8 buf[len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[2] = { struct i2c_msg msg[2] = {
{ {
.addr = priv->cfg->i2c_addr, .addr = priv->cfg->i2c_addr,
@@ -79,11 +89,18 @@ static int fc2580_rd_regs(struct fc2580_priv *priv, u8 reg, u8 *val, int len)
}, { }, {
.addr = priv->cfg->i2c_addr, .addr = priv->cfg->i2c_addr,
.flags = I2C_M_RD, .flags = I2C_M_RD,
.len = sizeof(buf), .len = len,
.buf = buf, .buf = buf,
} }
}; };
if (len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c rd reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
ret = i2c_transfer(priv->i2c, msg, 2); ret = i2c_transfer(priv->i2c, msg, 2);
if (ret == 2) { if (ret == 2) {
memcpy(val, buf, len); memcpy(val, buf, len);

View File

@@ -20,6 +20,9 @@
#include "tda18212.h" #include "tda18212.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
struct tda18212_priv { struct tda18212_priv {
struct tda18212_config *cfg; struct tda18212_config *cfg;
struct i2c_adapter *i2c; struct i2c_adapter *i2c;
@@ -32,16 +35,23 @@ static int tda18212_wr_regs(struct tda18212_priv *priv, u8 reg, u8 *val,
int len) int len)
{ {
int ret; int ret;
u8 buf[len+1]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->cfg->i2c_address, .addr = priv->cfg->i2c_address,
.flags = 0, .flags = 0,
.len = sizeof(buf), .len = 1 + len,
.buf = buf, .buf = buf,
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
buf[0] = reg; buf[0] = reg;
memcpy(&buf[1], val, len); memcpy(&buf[1], val, len);
@@ -61,7 +71,7 @@ static int tda18212_rd_regs(struct tda18212_priv *priv, u8 reg, u8 *val,
int len) int len)
{ {
int ret; int ret;
u8 buf[len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[2] = { struct i2c_msg msg[2] = {
{ {
.addr = priv->cfg->i2c_address, .addr = priv->cfg->i2c_address,
@@ -71,11 +81,18 @@ static int tda18212_rd_regs(struct tda18212_priv *priv, u8 reg, u8 *val,
}, { }, {
.addr = priv->cfg->i2c_address, .addr = priv->cfg->i2c_address,
.flags = I2C_M_RD, .flags = I2C_M_RD,
.len = sizeof(buf), .len = len,
.buf = buf, .buf = buf,
} }
}; };
if (len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c rd reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
ret = i2c_transfer(priv->i2c, msg, 2); ret = i2c_transfer(priv->i2c, msg, 2);
if (ret == 2) { if (ret == 2) {
memcpy(val, buf, len); memcpy(val, buf, len);

View File

@@ -20,11 +20,14 @@
#include "tda18218_priv.h" #include "tda18218_priv.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
/* write multiple registers */ /* write multiple registers */
static int tda18218_wr_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len) static int tda18218_wr_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len)
{ {
int ret = 0, len2, remaining; int ret = 0, len2, remaining;
u8 buf[1 + len]; u8 buf[MAX_XFER_SIZE];
struct i2c_msg msg[1] = { struct i2c_msg msg[1] = {
{ {
.addr = priv->cfg->i2c_address, .addr = priv->cfg->i2c_address,
@@ -33,6 +36,13 @@ static int tda18218_wr_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len)
} }
}; };
if (1 + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
for (remaining = len; remaining > 0; for (remaining = len; remaining > 0;
remaining -= (priv->cfg->i2c_wr_max - 1)) { remaining -= (priv->cfg->i2c_wr_max - 1)) {
len2 = remaining; len2 = remaining;
@@ -63,7 +73,7 @@ static int tda18218_wr_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len)
static int tda18218_rd_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len) static int tda18218_rd_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len)
{ {
int ret; int ret;
u8 buf[reg+len]; /* we must start read always from reg 0x00 */ u8 buf[MAX_XFER_SIZE]; /* we must start read always from reg 0x00 */
struct i2c_msg msg[2] = { struct i2c_msg msg[2] = {
{ {
.addr = priv->cfg->i2c_address, .addr = priv->cfg->i2c_address,
@@ -73,11 +83,18 @@ static int tda18218_rd_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len)
}, { }, {
.addr = priv->cfg->i2c_address, .addr = priv->cfg->i2c_address,
.flags = I2C_M_RD, .flags = I2C_M_RD,
.len = sizeof(buf), .len = reg + len,
.buf = buf, .buf = buf,
} }
}; };
if (reg + len > sizeof(buf)) {
dev_warn(&priv->i2c->dev,
"%s: i2c wr reg=%04x: len=%d is too big!\n",
KBUILD_MODNAME, reg, len);
return -EINVAL;
}
ret = i2c_transfer(priv->i2c, msg, 2); ret = i2c_transfer(priv->i2c, msg, 2);
if (ret == 2) { if (ret == 2) {
memcpy(val, &buf[reg], len); memcpy(val, &buf[reg], len);

View File

@@ -536,8 +536,8 @@ static int tda9887_status(struct dvb_frontend *fe)
unsigned char buf[1]; unsigned char buf[1];
int rc; int rc;
memset(buf,0,sizeof(buf)); rc = tuner_i2c_xfer_recv(&priv->i2c_props, buf, 1);
if (1 != (rc = tuner_i2c_xfer_recv(&priv->i2c_props,buf,1))) if (rc != 1)
tuner_info("i2c i/o error: rc == %d (should be 1)\n", rc); tuner_info("i2c i/o error: rc == %d (should be 1)\n", rc);
dump_read_message(fe, buf); dump_read_message(fe, buf);
return 0; return 0;

View File

@@ -24,6 +24,9 @@
#include <linux/dvb/frontend.h> #include <linux/dvb/frontend.h>
#include "dvb_frontend.h" #include "dvb_frontend.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 80
/* Registers (Write-only) */ /* Registers (Write-only) */
#define XREG_INIT 0x00 #define XREG_INIT 0x00
#define XREG_RF_FREQ 0x02 #define XREG_RF_FREQ 0x02
@@ -547,7 +550,10 @@ static int load_firmware(struct dvb_frontend *fe, unsigned int type,
{ {
struct xc2028_data *priv = fe->tuner_priv; struct xc2028_data *priv = fe->tuner_priv;
int pos, rc; int pos, rc;
unsigned char *p, *endp, buf[priv->ctrl.max_len]; unsigned char *p, *endp, buf[MAX_XFER_SIZE];
if (priv->ctrl.max_len > sizeof(buf))
priv->ctrl.max_len = sizeof(buf);
tuner_dbg("%s called\n", __func__); tuner_dbg("%s called\n", __func__);

View File

@@ -397,12 +397,13 @@ error:
return ret; return ret;
} }
#define AF9015_EEPROM_SIZE 256
/* hash (and dump) eeprom */ /* hash (and dump) eeprom */
static int af9015_eeprom_hash(struct dvb_usb_device *d) static int af9015_eeprom_hash(struct dvb_usb_device *d)
{ {
struct af9015_state *state = d_to_priv(d); struct af9015_state *state = d_to_priv(d);
int ret, i; int ret, i;
static const unsigned int AF9015_EEPROM_SIZE = 256;
u8 buf[AF9015_EEPROM_SIZE]; u8 buf[AF9015_EEPROM_SIZE];
struct req_t req = {READ_I2C, AF9015_I2C_EEPROM, 0, 0, 1, 1, NULL}; struct req_t req = {READ_I2C, AF9015_I2C_EEPROM, 0, 0, 1, 1, NULL};

View File

@@ -21,6 +21,9 @@
#include "af9035.h" #include "af9035.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
DVB_DEFINE_MOD_OPT_ADAPTER_NR(adapter_nr); DVB_DEFINE_MOD_OPT_ADAPTER_NR(adapter_nr);
static u16 af9035_checksum(const u8 *buf, size_t len) static u16 af9035_checksum(const u8 *buf, size_t len)
@@ -126,10 +129,16 @@ exit:
/* write multiple registers */ /* write multiple registers */
static int af9035_wr_regs(struct dvb_usb_device *d, u32 reg, u8 *val, int len) static int af9035_wr_regs(struct dvb_usb_device *d, u32 reg, u8 *val, int len)
{ {
u8 wbuf[6 + len]; u8 wbuf[MAX_XFER_SIZE];
u8 mbox = (reg >> 16) & 0xff; u8 mbox = (reg >> 16) & 0xff;
struct usb_req req = { CMD_MEM_WR, mbox, sizeof(wbuf), wbuf, 0, NULL }; struct usb_req req = { CMD_MEM_WR, mbox, sizeof(wbuf), wbuf, 0, NULL };
if (6 + len > sizeof(wbuf)) {
dev_warn(&d->udev->dev, "%s: i2c wr: len=%d is too big!\n",
KBUILD_MODNAME, len);
return -EOPNOTSUPP;
}
wbuf[0] = len; wbuf[0] = len;
wbuf[1] = 2; wbuf[1] = 2;
wbuf[2] = 0; wbuf[2] = 0;
@@ -228,9 +237,16 @@ static int af9035_i2c_master_xfer(struct i2c_adapter *adap,
msg[1].len); msg[1].len);
} else { } else {
/* I2C */ /* I2C */
u8 buf[5 + msg[0].len]; u8 buf[MAX_XFER_SIZE];
struct usb_req req = { CMD_I2C_RD, 0, sizeof(buf), struct usb_req req = { CMD_I2C_RD, 0, sizeof(buf),
buf, msg[1].len, msg[1].buf }; buf, msg[1].len, msg[1].buf };
if (5 + msg[0].len > sizeof(buf)) {
dev_warn(&d->udev->dev,
"%s: i2c xfer: len=%d is too big!\n",
KBUILD_MODNAME, msg[0].len);
return -EOPNOTSUPP;
}
req.mbox |= ((msg[0].addr & 0x80) >> 3); req.mbox |= ((msg[0].addr & 0x80) >> 3);
buf[0] = msg[1].len; buf[0] = msg[1].len;
buf[1] = msg[0].addr << 1; buf[1] = msg[0].addr << 1;
@@ -257,9 +273,16 @@ static int af9035_i2c_master_xfer(struct i2c_adapter *adap,
msg[0].len - 3); msg[0].len - 3);
} else { } else {
/* I2C */ /* I2C */
u8 buf[5 + msg[0].len]; u8 buf[MAX_XFER_SIZE];
struct usb_req req = { CMD_I2C_WR, 0, sizeof(buf), buf, struct usb_req req = { CMD_I2C_WR, 0, sizeof(buf), buf,
0, NULL }; 0, NULL };
if (5 + msg[0].len > sizeof(buf)) {
dev_warn(&d->udev->dev,
"%s: i2c xfer: len=%d is too big!\n",
KBUILD_MODNAME, msg[0].len);
return -EOPNOTSUPP;
}
req.mbox |= ((msg[0].addr & 0x80) >> 3); req.mbox |= ((msg[0].addr & 0x80) >> 3);
buf[0] = msg[0].len; buf[0] = msg[0].len;
buf[1] = msg[0].addr << 1; buf[1] = msg[0].addr << 1;

View File

@@ -23,6 +23,9 @@
#include "lgdt3305.h" #include "lgdt3305.h"
#include "lg2160.h" #include "lg2160.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
int dvb_usb_mxl111sf_debug; int dvb_usb_mxl111sf_debug;
module_param_named(debug, dvb_usb_mxl111sf_debug, int, 0644); module_param_named(debug, dvb_usb_mxl111sf_debug, int, 0644);
MODULE_PARM_DESC(debug, "set debugging level " MODULE_PARM_DESC(debug, "set debugging level "
@@ -57,7 +60,12 @@ int mxl111sf_ctrl_msg(struct dvb_usb_device *d,
{ {
int wo = (rbuf == NULL || rlen == 0); /* write-only */ int wo = (rbuf == NULL || rlen == 0); /* write-only */
int ret; int ret;
u8 sndbuf[1+wlen]; u8 sndbuf[MAX_XFER_SIZE];
if (1 + wlen > sizeof(sndbuf)) {
pr_warn("%s: len=%d is too big!\n", __func__, wlen);
return -EOPNOTSUPP;
}
pr_debug("%s(wlen = %d, rlen = %d)\n", __func__, wlen, rlen); pr_debug("%s(wlen = %d, rlen = %d)\n", __func__, wlen, rlen);

View File

@@ -43,6 +43,9 @@
#include "lgs8gxx.h" #include "lgs8gxx.h"
#include "atbm8830.h" #include "atbm8830.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
/* debug */ /* debug */
static int dvb_usb_cxusb_debug; static int dvb_usb_cxusb_debug;
module_param_named(debug, dvb_usb_cxusb_debug, int, 0644); module_param_named(debug, dvb_usb_cxusb_debug, int, 0644);
@@ -57,7 +60,14 @@ static int cxusb_ctrl_msg(struct dvb_usb_device *d,
u8 cmd, u8 *wbuf, int wlen, u8 *rbuf, int rlen) u8 cmd, u8 *wbuf, int wlen, u8 *rbuf, int rlen)
{ {
int wo = (rbuf == NULL || rlen == 0); /* write-only */ int wo = (rbuf == NULL || rlen == 0); /* write-only */
u8 sndbuf[1+wlen]; u8 sndbuf[MAX_XFER_SIZE];
if (1 + wlen > sizeof(sndbuf)) {
warn("i2c wr: len=%d is too big!\n",
wlen);
return -EOPNOTSUPP;
}
memset(sndbuf, 0, 1+wlen); memset(sndbuf, 0, 1+wlen);
sndbuf[0] = cmd; sndbuf[0] = cmd;
@@ -158,7 +168,13 @@ static int cxusb_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[],
if (msg[i].flags & I2C_M_RD) { if (msg[i].flags & I2C_M_RD) {
/* read only */ /* read only */
u8 obuf[3], ibuf[1+msg[i].len]; u8 obuf[3], ibuf[MAX_XFER_SIZE];
if (1 + msg[i].len > sizeof(ibuf)) {
warn("i2c rd: len=%d is too big!\n",
msg[i].len);
return -EOPNOTSUPP;
}
obuf[0] = 0; obuf[0] = 0;
obuf[1] = msg[i].len; obuf[1] = msg[i].len;
obuf[2] = msg[i].addr; obuf[2] = msg[i].addr;
@@ -172,7 +188,18 @@ static int cxusb_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[],
} else if (i+1 < num && (msg[i+1].flags & I2C_M_RD) && } else if (i+1 < num && (msg[i+1].flags & I2C_M_RD) &&
msg[i].addr == msg[i+1].addr) { msg[i].addr == msg[i+1].addr) {
/* write to then read from same address */ /* write to then read from same address */
u8 obuf[3+msg[i].len], ibuf[1+msg[i+1].len]; u8 obuf[MAX_XFER_SIZE], ibuf[MAX_XFER_SIZE];
if (3 + msg[i].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[i].len);
return -EOPNOTSUPP;
}
if (1 + msg[i + 1].len > sizeof(ibuf)) {
warn("i2c rd: len=%d is too big!\n",
msg[i + 1].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[i].len; obuf[0] = msg[i].len;
obuf[1] = msg[i+1].len; obuf[1] = msg[i+1].len;
obuf[2] = msg[i].addr; obuf[2] = msg[i].addr;
@@ -191,7 +218,13 @@ static int cxusb_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[],
i++; i++;
} else { } else {
/* write only */ /* write only */
u8 obuf[2+msg[i].len], ibuf; u8 obuf[MAX_XFER_SIZE], ibuf;
if (2 + msg[i].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[i].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[i].addr; obuf[0] = msg[i].addr;
obuf[1] = msg[i].len; obuf[1] = msg[i].len;
memcpy(&obuf[2], msg[i].buf, msg[i].len); memcpy(&obuf[2], msg[i].buf, msg[i].len);

View File

@@ -12,6 +12,9 @@
#include <linux/kconfig.h> #include <linux/kconfig.h>
#include "dibusb.h" #include "dibusb.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
static int debug; static int debug;
module_param(debug, int, 0644); module_param(debug, int, 0644);
MODULE_PARM_DESC(debug, "set debugging level (1=info (|-able))." DVB_USB_DEBUG_STATUS); MODULE_PARM_DESC(debug, "set debugging level (1=info (|-able))." DVB_USB_DEBUG_STATUS);
@@ -105,11 +108,16 @@ EXPORT_SYMBOL(dibusb2_0_power_ctrl);
static int dibusb_i2c_msg(struct dvb_usb_device *d, u8 addr, static int dibusb_i2c_msg(struct dvb_usb_device *d, u8 addr,
u8 *wbuf, u16 wlen, u8 *rbuf, u16 rlen) u8 *wbuf, u16 wlen, u8 *rbuf, u16 rlen)
{ {
u8 sndbuf[wlen+4]; /* lead(1) devaddr,direction(1) addr(2) data(wlen) (len(2) (when reading)) */ u8 sndbuf[MAX_XFER_SIZE]; /* lead(1) devaddr,direction(1) addr(2) data(wlen) (len(2) (when reading)) */
/* write only ? */ /* write only ? */
int wo = (rbuf == NULL || rlen == 0), int wo = (rbuf == NULL || rlen == 0),
len = 2 + wlen + (wo ? 0 : 2); len = 2 + wlen + (wo ? 0 : 2);
if (4 + wlen > sizeof(sndbuf)) {
warn("i2c wr: len=%d is too big!\n", wlen);
return -EOPNOTSUPP;
}
sndbuf[0] = wo ? DIBUSB_REQ_I2C_WRITE : DIBUSB_REQ_I2C_READ; sndbuf[0] = wo ? DIBUSB_REQ_I2C_WRITE : DIBUSB_REQ_I2C_READ;
sndbuf[1] = (addr << 1) | (wo ? 0 : 1); sndbuf[1] = (addr << 1) | (wo ? 0 : 1);

View File

@@ -30,6 +30,9 @@
#include "stb6100_proc.h" #include "stb6100_proc.h"
#include "m88rs2000.h" #include "m88rs2000.h"
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
#ifndef USB_PID_DW2102 #ifndef USB_PID_DW2102
#define USB_PID_DW2102 0x2102 #define USB_PID_DW2102 0x2102
#endif #endif
@@ -308,7 +311,14 @@ static int dw2102_earda_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg ms
case 2: { case 2: {
/* read */ /* read */
/* first write first register number */ /* first write first register number */
u8 ibuf[msg[1].len + 2], obuf[3]; u8 ibuf[MAX_XFER_SIZE], obuf[3];
if (2 + msg[1].len > sizeof(ibuf)) {
warn("i2c rd: len=%d is too big!\n",
msg[1].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[0].addr << 1; obuf[0] = msg[0].addr << 1;
obuf[1] = msg[0].len; obuf[1] = msg[0].len;
obuf[2] = msg[0].buf[0]; obuf[2] = msg[0].buf[0];
@@ -325,7 +335,14 @@ static int dw2102_earda_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg ms
switch (msg[0].addr) { switch (msg[0].addr) {
case 0x68: { case 0x68: {
/* write to register */ /* write to register */
u8 obuf[msg[0].len + 2]; u8 obuf[MAX_XFER_SIZE];
if (2 + msg[0].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[1].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[0].addr << 1; obuf[0] = msg[0].addr << 1;
obuf[1] = msg[0].len; obuf[1] = msg[0].len;
memcpy(obuf + 2, msg[0].buf, msg[0].len); memcpy(obuf + 2, msg[0].buf, msg[0].len);
@@ -335,7 +352,14 @@ static int dw2102_earda_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg ms
} }
case 0x61: { case 0x61: {
/* write to tuner */ /* write to tuner */
u8 obuf[msg[0].len + 2]; u8 obuf[MAX_XFER_SIZE];
if (2 + msg[0].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[1].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[0].addr << 1; obuf[0] = msg[0].addr << 1;
obuf[1] = msg[0].len; obuf[1] = msg[0].len;
memcpy(obuf + 2, msg[0].buf, msg[0].len); memcpy(obuf + 2, msg[0].buf, msg[0].len);
@@ -401,7 +425,14 @@ static int dw2104_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], i
default: { default: {
if (msg[j].flags == I2C_M_RD) { if (msg[j].flags == I2C_M_RD) {
/* read registers */ /* read registers */
u8 ibuf[msg[j].len + 2]; u8 ibuf[MAX_XFER_SIZE];
if (2 + msg[j].len > sizeof(ibuf)) {
warn("i2c rd: len=%d is too big!\n",
msg[j].len);
return -EOPNOTSUPP;
}
dw210x_op_rw(d->udev, 0xc3, dw210x_op_rw(d->udev, 0xc3,
(msg[j].addr << 1) + 1, 0, (msg[j].addr << 1) + 1, 0,
ibuf, msg[j].len + 2, ibuf, msg[j].len + 2,
@@ -430,7 +461,14 @@ static int dw2104_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], i
} while (len > 0); } while (len > 0);
} else { } else {
/* write registers */ /* write registers */
u8 obuf[msg[j].len + 2]; u8 obuf[MAX_XFER_SIZE];
if (2 + msg[j].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[j].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[j].addr << 1; obuf[0] = msg[j].addr << 1;
obuf[1] = msg[j].len; obuf[1] = msg[j].len;
memcpy(obuf + 2, msg[j].buf, msg[j].len); memcpy(obuf + 2, msg[j].buf, msg[j].len);
@@ -463,7 +501,13 @@ static int dw3101_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
case 2: { case 2: {
/* read */ /* read */
/* first write first register number */ /* first write first register number */
u8 ibuf[msg[1].len + 2], obuf[3]; u8 ibuf[MAX_XFER_SIZE], obuf[3];
if (2 + msg[1].len > sizeof(ibuf)) {
warn("i2c rd: len=%d is too big!\n",
msg[1].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[0].addr << 1; obuf[0] = msg[0].addr << 1;
obuf[1] = msg[0].len; obuf[1] = msg[0].len;
obuf[2] = msg[0].buf[0]; obuf[2] = msg[0].buf[0];
@@ -481,7 +525,13 @@ static int dw3101_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
case 0x60: case 0x60:
case 0x0c: { case 0x0c: {
/* write to register */ /* write to register */
u8 obuf[msg[0].len + 2]; u8 obuf[MAX_XFER_SIZE];
if (2 + msg[0].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[0].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[0].addr << 1; obuf[0] = msg[0].addr << 1;
obuf[1] = msg[0].len; obuf[1] = msg[0].len;
memcpy(obuf + 2, msg[0].buf, msg[0].len); memcpy(obuf + 2, msg[0].buf, msg[0].len);
@@ -563,7 +613,14 @@ static int s6x0_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
default: { default: {
if (msg[j].flags == I2C_M_RD) { if (msg[j].flags == I2C_M_RD) {
/* read registers */ /* read registers */
u8 ibuf[msg[j].len]; u8 ibuf[MAX_XFER_SIZE];
if (msg[j].len > sizeof(ibuf)) {
warn("i2c rd: len=%d is too big!\n",
msg[j].len);
return -EOPNOTSUPP;
}
dw210x_op_rw(d->udev, 0x91, 0, 0, dw210x_op_rw(d->udev, 0x91, 0, 0,
ibuf, msg[j].len, ibuf, msg[j].len,
DW210X_READ_MSG); DW210X_READ_MSG);
@@ -590,7 +647,14 @@ static int s6x0_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
} while (len > 0); } while (len > 0);
} else if (j < (num - 1)) { } else if (j < (num - 1)) {
/* write register addr before read */ /* write register addr before read */
u8 obuf[msg[j].len + 2]; u8 obuf[MAX_XFER_SIZE];
if (2 + msg[j].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[j].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[j + 1].len; obuf[0] = msg[j + 1].len;
obuf[1] = (msg[j].addr << 1); obuf[1] = (msg[j].addr << 1);
memcpy(obuf + 2, msg[j].buf, msg[j].len); memcpy(obuf + 2, msg[j].buf, msg[j].len);
@@ -602,7 +666,13 @@ static int s6x0_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
break; break;
} else { } else {
/* write registers */ /* write registers */
u8 obuf[msg[j].len + 2]; u8 obuf[MAX_XFER_SIZE];
if (2 + msg[j].len > sizeof(obuf)) {
warn("i2c wr: len=%d is too big!\n",
msg[j].len);
return -EOPNOTSUPP;
}
obuf[0] = msg[j].len + 1; obuf[0] = msg[j].len + 1;
obuf[1] = (msg[j].addr << 1); obuf[1] = (msg[j].addr << 1);
memcpy(obuf + 2, msg[j].buf, msg[j].len); memcpy(obuf + 2, msg[j].buf, msg[j].len);

View File

@@ -680,7 +680,8 @@ void uvc_video_clock_update(struct uvc_streaming *stream,
stream->dev->name, stream->dev->name,
sof >> 16, div_u64(((u64)sof & 0xffff) * 1000000LLU, 65536), sof >> 16, div_u64(((u64)sof & 0xffff) * 1000000LLU, 65536),
y, ts.tv_sec, ts.tv_nsec / NSEC_PER_USEC, y, ts.tv_sec, ts.tv_nsec / NSEC_PER_USEC,
v4l2_buf->timestamp.tv_sec, v4l2_buf->timestamp.tv_usec, v4l2_buf->timestamp.tv_sec,
(unsigned long)v4l2_buf->timestamp.tv_usec,
x1, first->host_sof, first->dev_sof, x1, first->host_sof, first->dev_sof,
x2, last->host_sof, last->dev_sof, y1, y2); x2, last->host_sof, last->dev_sof, y1, y2);

View File

@@ -189,30 +189,53 @@ void v4l2_async_notifier_unregister(struct v4l2_async_notifier *notifier)
struct v4l2_subdev *sd, *tmp; struct v4l2_subdev *sd, *tmp;
unsigned int notif_n_subdev = notifier->num_subdevs; unsigned int notif_n_subdev = notifier->num_subdevs;
unsigned int n_subdev = min(notif_n_subdev, V4L2_MAX_SUBDEVS); unsigned int n_subdev = min(notif_n_subdev, V4L2_MAX_SUBDEVS);
struct device *dev[n_subdev]; struct device **dev;
int i = 0; int i = 0;
if (!notifier->v4l2_dev) if (!notifier->v4l2_dev)
return; return;
dev = kmalloc(n_subdev * sizeof(*dev), GFP_KERNEL);
if (!dev) {
dev_err(notifier->v4l2_dev->dev,
"Failed to allocate device cache!\n");
}
mutex_lock(&list_lock); mutex_lock(&list_lock);
list_del(&notifier->list); list_del(&notifier->list);
list_for_each_entry_safe(sd, tmp, &notifier->done, async_list) { list_for_each_entry_safe(sd, tmp, &notifier->done, async_list) {
dev[i] = get_device(sd->dev); struct device *d;
d = get_device(sd->dev);
v4l2_async_cleanup(sd); v4l2_async_cleanup(sd);
/* If we handled USB devices, we'd have to lock the parent too */ /* If we handled USB devices, we'd have to lock the parent too */
device_release_driver(dev[i++]); device_release_driver(d);
if (notifier->unbind) if (notifier->unbind)
notifier->unbind(notifier, sd, sd->asd); notifier->unbind(notifier, sd, sd->asd);
/*
* Store device at the device cache, in order to call
* put_device() on the final step
*/
if (dev)
dev[i++] = d;
else
put_device(d);
} }
mutex_unlock(&list_lock); mutex_unlock(&list_lock);
/*
* Call device_attach() to reprobe devices
*
* NOTE: If dev allocation fails, i is 0, and the whole loop won't be
* executed.
*/
while (i--) { while (i--) {
struct device *d = dev[i]; struct device *d = dev[i];
@@ -228,6 +251,7 @@ void v4l2_async_notifier_unregister(struct v4l2_async_notifier *notifier)
} }
put_device(d); put_device(d);
} }
kfree(dev);
notifier->v4l2_dev = NULL; notifier->v4l2_dev = NULL;

View File

@@ -707,7 +707,8 @@ static irqreturn_t irq_handler(int i, void *blah)
pr_warn("ignoring spike: %d %d %lx %lx %lx %lx\n", pr_warn("ignoring spike: %d %d %lx %lx %lx %lx\n",
dcd, sense, dcd, sense,
tv.tv_sec, lasttv.tv_sec, tv.tv_sec, lasttv.tv_sec,
tv.tv_usec, lasttv.tv_usec); (unsigned long)tv.tv_usec,
(unsigned long)lasttv.tv_usec);
continue; continue;
} }
@@ -719,7 +720,8 @@ static irqreturn_t irq_handler(int i, void *blah)
pr_warn("%d %d %lx %lx %lx %lx\n", pr_warn("%d %d %lx %lx %lx %lx\n",
dcd, sense, dcd, sense,
tv.tv_sec, lasttv.tv_sec, tv.tv_sec, lasttv.tv_sec,
tv.tv_usec, lasttv.tv_usec); (unsigned long)tv.tv_usec,
(unsigned long)lasttv.tv_usec);
data = PULSE_MASK; data = PULSE_MASK;
} else if (deltv > 15) { } else if (deltv > 15) {
data = PULSE_MASK; /* really long time */ data = PULSE_MASK; /* really long time */
@@ -728,7 +730,8 @@ static irqreturn_t irq_handler(int i, void *blah)
pr_warn("AIEEEE: %d %d %lx %lx %lx %lx\n", pr_warn("AIEEEE: %d %d %lx %lx %lx %lx\n",
dcd, sense, dcd, sense,
tv.tv_sec, lasttv.tv_sec, tv.tv_sec, lasttv.tv_sec,
tv.tv_usec, lasttv.tv_usec); (unsigned long)tv.tv_usec,
(unsigned long)lasttv.tv_usec);
/* /*
* detecting pulse while this * detecting pulse while this
* MUST be a space! * MUST be a space!

View File

@@ -61,6 +61,9 @@
#include <media/lirc_dev.h> #include <media/lirc_dev.h>
#include <media/lirc.h> #include <media/lirc.h>
/* Max transfer size done by I2C transfer functions */
#define MAX_XFER_SIZE 64
struct IR; struct IR;
struct IR_rx { struct IR_rx {
@@ -941,7 +944,14 @@ static ssize_t read(struct file *filep, char *outbuf, size_t n, loff_t *ppos)
schedule(); schedule();
set_current_state(TASK_INTERRUPTIBLE); set_current_state(TASK_INTERRUPTIBLE);
} else { } else {
unsigned char buf[rbuf->chunk_size]; unsigned char buf[MAX_XFER_SIZE];
if (rbuf->chunk_size > sizeof(buf)) {
zilog_error("chunk_size is too big (%d)!\n",
rbuf->chunk_size);
ret = -EINVAL;
break;
}
m = lirc_buffer_read(rbuf, buf); m = lirc_buffer_read(rbuf, buf);
if (m == rbuf->chunk_size) { if (m == rbuf->chunk_size) {
ret = copy_to_user((void *)outbuf+written, buf, ret = copy_to_user((void *)outbuf+written, buf,