/* * si4713_powerdown - Powers the device down * @sdev: si4713_device structure for the device we are communicating */ static int si4713_powerdown(struct si4713_device *sdev) { int err; u8 resp[SI4713_PWDN_NRESP]; if (!sdev->power_state) return 0; err = si4713_send_command(sdev, SI4713_CMD_POWER_DOWN, NULL, 0, resp, ARRAY_SIZE(resp), DEFAULT_TIMEOUT); if (!err) { v4l2_dbg(1, debug, &sdev->sd, "Power down response: 0x%02x\n", resp[0]); v4l2_dbg(1, debug, &sdev->sd, "Device in reset mode\n"); if (gpio_is_valid(sdev->gpio_reset)) gpio_set_value(sdev->gpio_reset, 0); err = regulator_bulk_disable(ARRAY_SIZE(sdev->supplies), sdev->supplies); if (err) v4l2_err(&sdev->sd, "Failed to disable supplies: %d\n", err); sdev->power_state = POWER_OFF; } return err; }
static int sensor_subdev_open(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh) { struct sensor_info *info = to_sensor(sd); int ret = 0; struct platform_device *pdev; int irq = 0; v4l2_dbg(1, sensor_debug, sd, "%s", __func__); ret = sensor_set_clock(sd, FLITE_ID_C); if (ret < 0) { sensor_err("sensor set clock fail"); return ret; } ret = sensor_init_controls(info); if (ret < 0) { sensor_err("sensor init contols fail"); return ret; } fh->vfh.ctrl_handler = &info->handle; sensor_init_formats(sd, fh); pdev = get_mipi_csis_pdev(FLITE_ID_C); irq = platform_get_irq(pdev, 0); v4l2_dbg(1, sensor_debug, sd, "%s : mipi irq num : %d", __func__, irq); enable_irq(irq); return 0; }
static void m5mols_irq_work(struct work_struct *work) { struct m5mols_info *info = container_of(work, struct m5mols_info, work_irq); struct v4l2_subdev *sd = &info->sd; u8 reg; int ret; if (!is_powered(info) || m5mols_read_u8(sd, SYSTEM_INT_FACTOR, &info->interrupt)) return; switch (info->interrupt & REG_INT_MASK) { case REG_INT_AF: if (!is_available_af(info)) break; ret = m5mols_read_u8(sd, AF_STATUS, ®); v4l2_dbg(2, m5mols_debug, sd, "AF %s\n", reg == REG_AF_FAIL ? "Failed" : reg == REG_AF_SUCCESS ? "Success" : reg == REG_AF_IDLE ? "Idle" : "Busy"); break; case REG_INT_CAPTURE: if (!test_and_set_bit(ST_CAPT_IRQ, &info->flags)) wake_up_interruptible(&info->irq_waitq); v4l2_dbg(2, m5mols_debug, sd, "CAPTURE\n"); break; default: v4l2_dbg(2, m5mols_debug, sd, "Undefined: %02x\n", reg); break; }; }
static int ths7303_setvalue(struct v4l2_subdev *sd, v4l2_std_id std) { int err = 0; u8 val; struct i2c_client *client; client = v4l2_get_subdevdata(sd); if (std & (V4L2_STD_ALL & ~V4L2_STD_SECAM)) { val = 0x02; v4l2_dbg(1, debug, sd, "setting value for SDTV format\n"); } else { val = 0x00; v4l2_dbg(1, debug, sd, "disabling all channels\n"); } err |= i2c_smbus_write_byte_data(client, 0x01, val); err |= i2c_smbus_write_byte_data(client, 0x02, val); err |= i2c_smbus_write_byte_data(client, 0x03, val); if (err) v4l2_err(sd, "write failed\n"); return err; }
/* * si4713_tx_tune_status- Returns the status of the tx_tune_freq, tx_tune_mea or * tx_tune_power commands. This command return the current * frequency, output voltage in dBuV, the antenna tunning * capacitance value and the received noise level. The * command also clears the stcint interrupt bit when the * first bit of its arguments is high. * @sdev: si4713_device structure for the device we are communicating * @intack: 0x01 to clear the seek/tune complete interrupt status indicator. * @frequency: returned frequency * @power: returned power * @antcap: returned antenna capacitance * @noise: returned noise level */ static int si4713_tx_tune_status(struct si4713_device *sdev, u8 intack, u16 *frequency, u8 *power, u8 *antcap, u8 *noise) { int err; u8 val[SI4713_TXSTATUS_NRESP]; /* * .First byte = intack bit */ const u8 args[SI4713_TXSTATUS_NARGS] = { intack & SI4713_INTACK_MASK, }; err = si4713_send_command(sdev, SI4713_CMD_TX_TUNE_STATUS, args, ARRAY_SIZE(args), val, ARRAY_SIZE(val), DEFAULT_TIMEOUT); if (!err) { v4l2_dbg(1, debug, &sdev->sd, "%s: status=0x%02x\n", __func__, val[0]); *frequency = compose_u16(val[2], val[3]); sdev->frequency = *frequency; *power = val[5]; *antcap = val[6]; *noise = val[7]; v4l2_dbg(1, debug, &sdev->sd, "%s: response: %d x 10 kHz " "(power %d, antcap %d, rnl %d)\n", __func__, *frequency, *power, *antcap, *noise); } return err; }
/* * si4713_tx_rds_buff - Loads the RDS group buffer FIFO or circular buffer. * @sdev: si4713_device structure for the device we are communicating * @mode: the buffer operation mode. * @rdsb: RDS Block B * @rdsc: RDS Block C * @rdsd: RDS Block D * @cbleft: returns the number of available circular buffer blocks minus the * number of used circular buffer blocks. */ static int si4713_tx_rds_buff(struct si4713_device *sdev, u8 mode, u16 rdsb, u16 rdsc, u16 rdsd, s8 *cbleft) { int err; u8 val[SI4713_RDSBUFF_NRESP]; const u8 args[SI4713_RDSBUFF_NARGS] = { mode & SI4713_RDSBUFF_MODE_MASK, msb(rdsb), lsb(rdsb), msb(rdsc), lsb(rdsc), msb(rdsd), lsb(rdsd), }; err = si4713_send_command(sdev, SI4713_CMD_TX_RDS_BUFF, args, ARRAY_SIZE(args), val, ARRAY_SIZE(val), DEFAULT_TIMEOUT); if (!err) { v4l2_dbg(1, debug, &sdev->sd, "%s: status=0x%02x\n", __func__, val[0]); *cbleft = (s8)val[2] - val[3]; v4l2_dbg(1, debug, &sdev->sd, "%s: response: interrupts" " 0x%02x cb avail: %d cb used %d fifo avail" " %d fifo used %d\n", __func__, val[1], val[2], val[3], val[4], val[5]); } return err; }
/* Receiver */ static int cx25840_ir_rx_read(struct v4l2_subdev *sd, u8 *buf, size_t count, ssize_t *num) { struct cx25840_ir_state *ir_state = to_ir_state(sd); bool invert; u16 divider; unsigned int i, n; union cx25840_ir_fifo_rec *p; unsigned u, v, w; if (ir_state == NULL) return -ENODEV; invert = (bool) atomic_read(&ir_state->rx_invert); divider = (u16) atomic_read(&ir_state->rxclk_divider); n = count / sizeof(union cx25840_ir_fifo_rec) * sizeof(union cx25840_ir_fifo_rec); if (n == 0) { *num = 0; return 0; } n = kfifo_out_locked(&ir_state->rx_kfifo, buf, n, &ir_state->rx_kfifo_lock); n /= sizeof(union cx25840_ir_fifo_rec); *num = n * sizeof(union cx25840_ir_fifo_rec); for (p = (union cx25840_ir_fifo_rec *) buf, i = 0; i < n; p++, i++) { if ((p->hw_fifo_data & FIFO_RXTX_RTO) == FIFO_RXTX_RTO) { /* Assume RTO was because of no IR light input */ u = 0; w = 1; } else { u = (p->hw_fifo_data & FIFO_RXTX_LVL) ? 1 : 0; if (invert) u = u ? 0 : 1; w = 0; } v = (unsigned) pulse_width_count_to_ns( (u16) (p->hw_fifo_data & FIFO_RXTX), divider); if (v > IR_MAX_DURATION) v = IR_MAX_DURATION; init_ir_raw_event(&p->ir_core_data); p->ir_core_data.pulse = u; p->ir_core_data.duration = v; p->ir_core_data.timeout = w; v4l2_dbg(2, ir_debug, sd, "rx read: %10u ns %s %s\n", v, u ? "mark" : "space", w ? "(timed out)" : ""); if (w) v4l2_dbg(2, ir_debug, sd, "rx read: end of rx\n"); } return 0; }
/* * si4713_powerup - Powers the device up * @sdev: si4713_device structure for the device we are communicating */ static int si4713_powerup(struct si4713_device *sdev) { int err; u8 resp[SI4713_PWUP_NRESP]; /* * .First byte = Enabled interrupts and boot function * .Second byte = Input operation mode */ const u8 args[SI4713_PWUP_NARGS] = { SI4713_PWUP_CTSIEN | SI4713_PWUP_GPO2OEN | SI4713_PWUP_FUNC_TX, SI4713_PWUP_OPMOD_ANALOG, }; if (sdev->power_state) return 0; err = regulator_bulk_enable(ARRAY_SIZE(sdev->supplies), sdev->supplies); if (err) { v4l2_err(&sdev->sd, "Failed to enable supplies: %d\n", err); return err; } if (gpio_is_valid(sdev->gpio_reset)) { udelay(50); gpio_set_value(sdev->gpio_reset, 1); } err = si4713_send_command(sdev, SI4713_CMD_POWER_UP, args, ARRAY_SIZE(args), resp, ARRAY_SIZE(resp), TIMEOUT_POWER_UP); if (!err) { v4l2_dbg(1, debug, &sdev->sd, "Powerup response: 0x%02x\n", resp[0]); v4l2_dbg(1, debug, &sdev->sd, "Device in power up mode\n"); sdev->power_state = POWER_ON; err = si4713_write_property(sdev, SI4713_GPO_IEN, SI4713_STC_INT | SI4713_CTS); } else { if (gpio_is_valid(sdev->gpio_reset)) gpio_set_value(sdev->gpio_reset, 0); err = regulator_bulk_disable(ARRAY_SIZE(sdev->supplies), sdev->supplies); if (err) v4l2_err(&sdev->sd, "Failed to disable supplies: %d\n", err); } return err; }
/* Receiver */ static int cx23888_ir_rx_read(struct v4l2_subdev *sd, u8 *buf, size_t count, ssize_t *num) { struct cx23888_ir_state *state = to_state(sd); bool invert = (bool) atomic_read(&state->rx_invert); u16 divider = (u16) atomic_read(&state->rxclk_divider); unsigned int i, n; u32 *p; u32 u, v; n = count / sizeof(u32) * sizeof(u32); if (n == 0) { *num = 0; return 0; } #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 33) n = kfifo_get(state->rx_kfifo, buf, n); #else n = kfifo_out_locked(&state->rx_kfifo, buf, n, &state->rx_kfifo_lock); #endif n /= sizeof(u32); *num = n * sizeof(u32); for (p = (u32 *) buf, i = 0; i < n; p++, i++) { if ((*p & FIFO_RXTX_RTO) == FIFO_RXTX_RTO) { *p = V4L2_SUBDEV_IR_PULSE_RX_SEQ_END; v4l2_dbg(2, ir_888_debug, sd, "rx read: end of rx\n"); continue; } u = (*p & FIFO_RXTX_LVL) ? V4L2_SUBDEV_IR_PULSE_LEVEL_MASK : 0; if (invert) u = u ? 0 : V4L2_SUBDEV_IR_PULSE_LEVEL_MASK; v = (u32) pulse_width_count_to_ns((u16) (*p & FIFO_RXTX), divider); if (v >= V4L2_SUBDEV_IR_PULSE_MAX_WIDTH_NS) v = V4L2_SUBDEV_IR_PULSE_MAX_WIDTH_NS - 1; *p = u | v; v4l2_dbg(2, ir_888_debug, sd, "rx read: %10u ns %s\n", v, u ? "mark" : "space"); } return 0; }
static int mt9v011_s_config(struct v4l2_subdev *sd, int dumb, void *data) { struct mt9v011 *core = to_mt9v011(sd); unsigned *xtal = data; v4l2_dbg(1, debug, sd, "s_config called\n"); if (xtal) { core->xtal = *xtal; v4l2_dbg(1, debug, sd, "xtal set to %d.%03d MHz\n", *xtal / 1000000, (*xtal / 1000) % 1000); } return 0; }
/* * si4713_tx_tune_power - Sets the RF voltage level between 88 and 115 dBuV in * 1 dB units. A value of 0x00 indicates off. The command * also sets the antenna tuning capacitance. A value of 0 * indicates autotuning, and a value of 1 - 191 indicates * a manual override, which results in a tuning * capacitance of 0.25 pF x @antcap. * @sdev: si4713_device structure for the device we are communicating * @power: tuning power (88 - 115 dBuV, unit/step 1 dB) * @antcap: value of antenna tuning capacitor (0 - 191) */ static int si4713_tx_tune_power(struct si4713_device *sdev, u8 power, u8 antcap) { int err; u8 val[SI4713_TXPWR_NRESP]; /* * .First byte = 0 * .Second byte = 0 * .Third byte = power * .Fourth byte = antcap */ const u8 args[SI4713_TXPWR_NARGS] = { 0x00, 0x00, power, antcap, }; if (((power > 0) && (power < SI4713_MIN_POWER)) || power > SI4713_MAX_POWER || antcap > SI4713_MAX_ANTCAP) return -EDOM; err = si4713_send_command(sdev, SI4713_CMD_TX_TUNE_POWER, args, ARRAY_SIZE(args), val, ARRAY_SIZE(val), DEFAULT_TIMEOUT); if (err < 0) return err; v4l2_dbg(1, debug, &sdev->sd, "%s: power=0x%02x antcap=0x%02x status=0x%02x\n", __func__, power, antcap, val[0]); return si4713_wait_stc(sdev, TIMEOUT_TX_TUNE_POWER); }
static int tda9840_s_tuner(struct v4l2_subdev *sd, const struct v4l2_tuner *t) { int stat = tda9840_status(sd); int byte; if (t->index) return -EINVAL; stat = stat < 0 ? 0 : stat; if (stat == 0 || stat == 0x60) /* mono input */ byte = TDA9840_SET_MONO; else if (stat == 0x40) /* stereo input */ byte = (t->audmode == V4L2_TUNER_MODE_MONO) ? TDA9840_SET_MONO : TDA9840_SET_STEREO; else { /* bilingual */ switch (t->audmode) { case V4L2_TUNER_MODE_LANG1_LANG2: byte = TDA9840_SET_BOTH; break; case V4L2_TUNER_MODE_LANG2: byte = TDA9840_SET_LANG2; break; default: byte = TDA9840_SET_LANG1; break; } } v4l2_dbg(1, debug, sd, "TDA9840_SWITCH: 0x%02x\n", byte); tda9840_write(sd, SWITCH, byte); return 0; }
/** * m5mols_fw_start - M-5MOLS internal ARM controller initialization * * Execute the M-5MOLS internal ARM controller initialization sequence. * This function should be called after the supply voltage has been * applied and before any requests to the device are made. */ static int m5mols_fw_start(struct v4l2_subdev *sd) { struct m5mols_info *info = to_m5mols(sd); int ret; atomic_set(&info->irq_done, 0); /* Wait until I2C slave is initialized in Flash Writer mode */ ret = m5mols_busy_wait(sd, FLASH_CAM_START, REG_IN_FLASH_MODE, M5MOLS_I2C_RDY_WAIT_FL | 0xff, -1); if (!ret) ret = m5mols_write(sd, FLASH_CAM_START, REG_START_ARM_BOOT); if (!ret) ret = m5mols_wait_interrupt(sd, REG_INT_MODE, 2000); if (ret < 0) return ret; info->isp_ready = 1; ret = m5mols_get_version(sd); if (!ret) ret = m5mols_update_fw(sd, m5mols_sensor_power); if (ret) return ret; v4l2_dbg(1, m5mols_debug, sd, "Success ARM Booting\n"); ret = m5mols_write(sd, PARM_INTERFACE, REG_INTERFACE_MIPI); if (!ret) ret = m5mols_enable_interrupt(sd, REG_INT_AF | REG_INT_CAPTURE); return ret; }
/* * si4713_read_property - reads a si4713 property * @sdev: si4713_device structure for the device we are communicating * @prop: property identification number * @pv: property value to be returned on success */ static int si4713_read_property(struct si4713_device *sdev, u16 prop, u32 *pv) { int err; u8 val[SI4713_GET_PROP_NRESP]; /* * .First byte = 0 * .Second byte = property's MSB * .Third byte = property's LSB */ const u8 args[SI4713_GET_PROP_NARGS] = { 0x00, msb(prop), lsb(prop), }; err = si4713_send_command(sdev, SI4713_CMD_GET_PROPERTY, args, ARRAY_SIZE(args), val, ARRAY_SIZE(val), DEFAULT_TIMEOUT); if (err < 0) return err; *pv = compose_u16(val[2], val[3]); v4l2_dbg(1, debug, &sdev->sd, "%s: property=0x%02x value=0x%02x status=0x%02x\n", __func__, prop, *pv, val[0]); return err; }
/* * si4713_tx_tune_power - Sets the RF voltage level between 88 and 120 dBuV in * 1 dB units. A value of 0x00 indicates off. The command * also sets the antenna tuning capacitance. A value of 0 * indicates autotuning, and a value of 1 - 191 indicates * a manual override, which results in a tuning * capacitance of 0.25 pF x @antcap. * @sdev: si4713_device structure for the device we are communicating * @power: tuning power (88 - 120 dBuV, unit/step 1 dB) * @antcap: value of antenna tuning capacitor (0 - 191) */ static int si4713_tx_tune_power(struct si4713_device *sdev, u8 power, u8 antcap) { int err; u8 val[SI4713_TXPWR_NRESP]; /* * .First byte = 0 * .Second byte = 0 * .Third byte = power * .Fourth byte = antcap */ u8 args[SI4713_TXPWR_NARGS] = { 0x00, 0x00, power, antcap, }; /* Map power values 1-87 to MIN_POWER (88) */ if (power > 0 && power < SI4713_MIN_POWER) args[2] = power = SI4713_MIN_POWER; err = si4713_send_command(sdev, SI4713_CMD_TX_TUNE_POWER, args, ARRAY_SIZE(args), val, ARRAY_SIZE(val), DEFAULT_TIMEOUT); if (err < 0) return err; v4l2_dbg(1, debug, &sdev->sd, "%s: power=0x%02x antcap=0x%02x status=0x%02x\n", __func__, power, antcap, val[0]); return si4713_wait_stc(sdev, TIMEOUT_TX_TUNE_POWER); }
static int vpbe_buffer_prepare(struct videobuf_queue *q, struct videobuf_buffer *vb, enum v4l2_field field) { struct vpbe_fh *fh = q->priv_data; struct vpbe_layer *layer = fh->layer; struct vpbe_device *vpbe_dev = fh->disp_dev->vpbe_dev; unsigned long addr; int ret; v4l2_dbg(1, debug, &vpbe_dev->v4l2_dev, "vpbe_buffer_prepare\n"); if (VIDEOBUF_NEEDS_INIT == vb->state) { vb->width = layer->pix_fmt.width; vb->height = layer->pix_fmt.height; vb->size = layer->pix_fmt.sizeimage; vb->field = field; ret = videobuf_iolock(q, vb, NULL); if (ret < 0) { v4l2_err(&vpbe_dev->v4l2_dev, "Failed to map \ user address\n"); return -EINVAL; }
static int tda9840_s_tuner(struct v4l2_subdev *sd, struct v4l2_tuner *t) { int byte; if (t->index) return -EINVAL; switch (t->audmode) { case V4L2_TUNER_MODE_STEREO: byte = TDA9840_SET_STEREO; break; case V4L2_TUNER_MODE_LANG1_LANG2: byte = TDA9840_SET_BOTH; break; case V4L2_TUNER_MODE_LANG1: byte = TDA9840_SET_LANG1; break; case V4L2_TUNER_MODE_LANG2: byte = TDA9840_SET_LANG2; break; default: byte = TDA9840_SET_MONO; break; } v4l2_dbg(1, debug, sd, "TDA9840_SWITCH: 0x%02x\n", byte); tda9840_write(sd, SWITCH, byte); return 0; }
static int tda9840_probe(struct i2c_client *client, const struct i2c_device_id *id) { struct v4l2_subdev *sd; int result; int byte; /* let's see whether this adapter can support what we need */ if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_READ_BYTE_DATA | I2C_FUNC_SMBUS_WRITE_BYTE_DATA)) return -EIO; v4l_info(client, "chip found @ 0x%x (%s)\n", client->addr << 1, client->adapter->name); sd = kmalloc(sizeof(struct v4l2_subdev), GFP_KERNEL); if (sd == NULL) return -ENOMEM; v4l2_i2c_subdev_init(sd, client, &tda9840_ops); /* set initial values for level & stereo - adjustment, mode */ byte = 0; result = tda9840_ioctl(sd, TDA9840_LEVEL_ADJUST, &byte); result |= tda9840_ioctl(sd, TDA9840_STEREO_ADJUST, &byte); tda9840_write(sd, SWITCH, TDA9840_SET_STEREO); if (result) { v4l2_dbg(1, debug, sd, "could not initialize tda9840\n"); kfree(sd); return -ENODEV; } return 0; }
int get_input_lines_info(struct hdpvr_device *dev) { #ifdef HDPVR_DEBUG char print_buf[9]; #endif int ret, lines; mutex_lock(&dev->usbc_mutex); ret = usb_control_msg(dev->udev, usb_rcvctrlpipe(dev->udev, 0), 0x81, 0x80 | 0x38, 0x1800, 0x0003, dev->usbc_buf, 3, 1000); #ifdef HDPVR_DEBUG if (hdpvr_debug & MSG_INFO) { hex_dump_to_buffer(dev->usbc_buf, 3, 16, 1, print_buf, sizeof(print_buf), 0); v4l2_dbg(MSG_INFO, hdpvr_debug, &dev->v4l2_dev, "get input lines info returned: %d, %s\n", ret, print_buf); } #endif lines = dev->usbc_buf[1] << 8 | dev->usbc_buf[0]; mutex_unlock(&dev->usbc_mutex); return lines; }
/* * si4713_wait_stc - Waits STC interrupt and clears status bits. Useful * for TX_TUNE_POWER, TX_TUNE_FREQ and TX_TUNE_MEAS * @sdev: si4713_device structure for the device we are communicating * @usecs: timeout to wait for STC interrupt signal */ static int si4713_wait_stc(struct si4713_device *sdev, const int usecs) { int err; u8 resp[SI4713_GET_STATUS_NRESP]; /* Wait response from STC interrupt */ if (!wait_for_completion_timeout(&sdev->work, usecs_to_jiffies(usecs) + 1)) v4l2_warn(&sdev->sd, "%s: device took too much time to answer (%d usec).\n", __func__, usecs); /* Clear status bits */ err = si4713_send_command(sdev, SI4713_CMD_GET_INT_STATUS, NULL, 0, resp, ARRAY_SIZE(resp), DEFAULT_TIMEOUT); if (err < 0) goto exit; v4l2_dbg(1, debug, &sdev->sd, "%s: status bits: 0x%02x\n", __func__, resp[0]); if (!(resp[0] & SI4713_STC_INT)) err = -EIO; exit: return err; }
/* * si4713_tx_tune_freq - Sets the state of the RF carrier and sets the tuning * frequency between 76 and 108 MHz in 10 kHz units and * steps of 50 kHz. * @sdev: si4713_device structure for the device we are communicating * @frequency: desired frequency (76 - 108 MHz, unit 10 KHz, step 50 kHz) */ static int si4713_tx_tune_freq(struct si4713_device *sdev, u16 frequency) { int err; u8 val[SI4713_TXFREQ_NRESP]; /* * .First byte = 0 * .Second byte = frequency's MSB * .Third byte = frequency's LSB */ const u8 args[SI4713_TXFREQ_NARGS] = { 0x00, msb(frequency), lsb(frequency), }; err = si4713_send_command(sdev, SI4713_CMD_TX_TUNE_FREQ, args, ARRAY_SIZE(args), val, ARRAY_SIZE(val), DEFAULT_TIMEOUT); if (err < 0) return err; v4l2_dbg(1, debug, &sdev->sd, "%s: frequency=0x%02x status=0x%02x\n", __func__, frequency, val[0]); err = si4713_wait_stc(sdev, TIMEOUT_TX_TUNE); if (err < 0) return err; return compose_u16(args[1], args[2]); }
/* * si4713_tx_rds_ps - Loads the program service buffer. * @sdev: si4713_device structure for the device we are communicating * @psid: program service id to be loaded. * @pschar: assumed 4 size char array to be loaded into the program service */ static int si4713_tx_rds_ps(struct si4713_device *sdev, u8 psid, unsigned char *pschar) { int err; u8 val[SI4713_RDSPS_NRESP]; const u8 args[SI4713_RDSPS_NARGS] = { psid & SI4713_RDSPS_PSID_MASK, pschar[0], pschar[1], pschar[2], pschar[3], }; err = si4713_send_command(sdev, SI4713_CMD_TX_RDS_PS, args, ARRAY_SIZE(args), val, ARRAY_SIZE(val), DEFAULT_TIMEOUT); if (err < 0) return err; v4l2_dbg(1, debug, &sdev->sd, "%s: status=0x%02x\n", __func__, val[0]); return err; }
static int mt9v011_g_ctrl(struct v4l2_subdev *sd, struct v4l2_control *ctrl) { struct mt9v011 *core = to_mt9v011(sd); v4l2_dbg(1, debug, sd, "g_ctrl called\n"); switch (ctrl->id) { case V4L2_CID_GAIN: ctrl->value = core->global_gain; return 0; case V4L2_CID_EXPOSURE: ctrl->value = core->exposure; return 0; case V4L2_CID_RED_BALANCE: ctrl->value = core->red_bal; return 0; case V4L2_CID_BLUE_BALANCE: ctrl->value = core->blue_bal; return 0; case V4L2_CID_HFLIP: ctrl->value = core->hflip ? 1 : 0; return 0; case V4L2_CID_VFLIP: ctrl->value = core->vflip ? 1 : 0; return 0; } return -EINVAL; }
static void calc_fps(struct v4l2_subdev *sd, u32 *numerator, u32 *denominator) { struct mt9v011 *core = to_mt9v011(sd); unsigned height, width, hblank, vblank, speed; unsigned row_time, t_time; u64 frames_per_ms; unsigned tmp; height = mt9v011_read(sd, R03_MT9V011_HEIGHT); width = mt9v011_read(sd, R04_MT9V011_WIDTH); hblank = mt9v011_read(sd, R05_MT9V011_HBLANK); vblank = mt9v011_read(sd, R06_MT9V011_VBLANK); speed = mt9v011_read(sd, R0A_MT9V011_CLK_SPEED); row_time = (width + 113 + hblank) * (speed + 2); t_time = row_time * (height + vblank + 1); frames_per_ms = core->xtal * 1000l; do_div(frames_per_ms, t_time); tmp = frames_per_ms; v4l2_dbg(1, debug, sd, "Programmed to %u.%03u fps (%d pixel clcks)\n", tmp / 1000, tmp % 1000, t_time); if (numerator && denominator) { *numerator = 1000; *denominator = (u32)frames_per_ms; } }
int get_video_info(struct hdpvr_device *dev, struct hdpvr_video_info *vidinf) { int ret; vidinf->valid = false; mutex_lock(&dev->usbc_mutex); ret = usb_control_msg(dev->udev, usb_rcvctrlpipe(dev->udev, 0), 0x81, 0x80 | 0x38, 0x1400, 0x0003, dev->usbc_buf, 5, 1000); #ifdef HDPVR_DEBUG if (hdpvr_debug & MSG_INFO) v4l2_dbg(MSG_INFO, hdpvr_debug, &dev->v4l2_dev, "get video info returned: %d, %5ph\n", ret, dev->usbc_buf); #endif mutex_unlock(&dev->usbc_mutex); if (ret < 0) return ret; vidinf->width = dev->usbc_buf[1] << 8 | dev->usbc_buf[0]; vidinf->height = dev->usbc_buf[3] << 8 | dev->usbc_buf[2]; vidinf->fps = dev->usbc_buf[4]; vidinf->valid = vidinf->width && vidinf->height && vidinf->fps; return 0; }
static void __configure_output(struct atomisp_sub_device *isp_subdev, unsigned int width, unsigned int height, enum ia_css_frame_format format, enum ia_css_pipe_id pipe_id) { isp_subdev->css2_basis.curr_pipe = pipe_id; isp_subdev->css2_basis.pipe_configs[pipe_id].mode = __pipe_id_to_pipe_mode(pipe_id); isp_subdev->css2_basis.update_pipe[pipe_id] = true; isp_subdev->css2_basis.pipe_configs[pipe_id]. output_info.res.width = width; isp_subdev->css2_basis.pipe_configs[pipe_id]. output_info.res.height = height; isp_subdev->css2_basis.pipe_configs[pipe_id]. output_info.format = format; if (width * height > isp_subdev->css2_basis.stream_config. effective_res.width * isp_subdev->css2_basis.stream_config. effective_res.height) { isp_subdev->css2_basis.stream_config. effective_res.width = width; isp_subdev->css2_basis.stream_config. effective_res.height = height; } v4l2_dbg(3, dbg_level, &atomisp_dev, "configuring pipe[%d] output info w=%d.h=%d.f=%d.\n", pipe_id, width, height, format); }
static const struct fimc_fmt *fimc_lite_try_format(struct fimc_lite *fimc, u32 *width, u32 *height, u32 *code, u32 *fourcc, int pad) { struct flite_variant *variant = fimc->variant; const struct fimc_fmt *fmt; fmt = fimc_lite_find_format(fourcc, code, 0); if (WARN_ON(!fmt)) return NULL; if (code) *code = fmt->mbus_code; if (fourcc) *fourcc = fmt->fourcc; if (pad == FLITE_SD_PAD_SINK) { v4l_bound_align_image(width, 8, variant->max_width, ffs(variant->out_width_align) - 1, height, 0, variant->max_height, 0, 0); } else { v4l_bound_align_image(width, 8, fimc->inp_frame.rect.width, ffs(variant->out_width_align) - 1, height, 0, fimc->inp_frame.rect.height, 0, 0); } v4l2_dbg(1, debug, &fimc->subdev, "code: 0x%x, %dx%d\n", code ? *code : 0, *width, *height); return fmt; }
static int fimc_lite_subdev_set_selection(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh, struct v4l2_subdev_selection *sel) { struct fimc_lite *fimc = v4l2_get_subdevdata(sd); struct flite_frame *f = &fimc->inp_frame; int ret = 0; if (sel->target != V4L2_SEL_TGT_CROP || sel->pad != FLITE_SD_PAD_SINK) return -EINVAL; mutex_lock(&fimc->lock); fimc_lite_try_crop(fimc, &sel->r); if (sel->which == V4L2_SUBDEV_FORMAT_TRY) { *v4l2_subdev_get_try_crop(fh, sel->pad) = sel->r; } else { unsigned long flags; spin_lock_irqsave(&fimc->slock, flags); f->rect = sel->r; /* Same crop rectangle on the source pad */ fimc->out_frame.rect = sel->r; set_bit(ST_FLITE_CONFIG, &fimc->state); spin_unlock_irqrestore(&fimc->slock, flags); } mutex_unlock(&fimc->lock); v4l2_dbg(1, debug, sd, "%s: (%d,%d) %dx%d, f_w: %d, f_h: %d", __func__, f->rect.left, f->rect.top, f->rect.width, f->rect.height, f->f_width, f->f_height); return ret; }
static int fimc_lite_subdev_get_selection(struct v4l2_subdev *sd, struct v4l2_subdev_fh *fh, struct v4l2_subdev_selection *sel) { struct fimc_lite *fimc = v4l2_get_subdevdata(sd); struct flite_frame *f = &fimc->inp_frame; if ((sel->target != V4L2_SEL_TGT_CROP && sel->target != V4L2_SEL_TGT_CROP_BOUNDS) || sel->pad != FLITE_SD_PAD_SINK) return -EINVAL; if (sel->which == V4L2_SUBDEV_FORMAT_TRY) { sel->r = *v4l2_subdev_get_try_crop(fh, sel->pad); return 0; } mutex_lock(&fimc->lock); if (sel->target == V4L2_SEL_TGT_CROP) { sel->r = f->rect; } else { sel->r.left = 0; sel->r.top = 0; sel->r.width = f->f_width; sel->r.height = f->f_height; } mutex_unlock(&fimc->lock); v4l2_dbg(1, debug, sd, "%s: (%d,%d) %dx%d, f_w: %d, f_h: %d", __func__, f->rect.left, f->rect.top, f->rect.width, f->rect.height, f->f_width, f->f_height); return 0; }
/* Capture subdev media entity operations */ static int fimc_lite_link_setup(struct media_entity *entity, const struct media_pad *local, const struct media_pad *remote, u32 flags) { struct v4l2_subdev *sd = media_entity_to_v4l2_subdev(entity); struct fimc_lite *fimc = v4l2_get_subdevdata(sd); unsigned int remote_ent_type = media_entity_type(remote->entity); int ret = 0; if (WARN_ON(fimc == NULL)) return 0; v4l2_dbg(1, debug, sd, "%s: %s --> %s, flags: 0x%x. source_id: 0x%x\n", __func__, remote->entity->name, local->entity->name, flags, fimc->source_subdev_grp_id); switch (local->index) { case FLITE_SD_PAD_SINK: if (remote_ent_type != MEDIA_ENT_T_V4L2_SUBDEV) { ret = -EINVAL; break; } if (flags & MEDIA_LNK_FL_ENABLED) { if (fimc->source_subdev_grp_id == 0) fimc->source_subdev_grp_id = sd->grp_id; else ret = -EBUSY; } else { fimc->source_subdev_grp_id = 0; fimc->sensor = NULL; } break; case FLITE_SD_PAD_SOURCE_DMA: if (!(flags & MEDIA_LNK_FL_ENABLED)) atomic_set(&fimc->out_path, FIMC_IO_NONE); else if (remote_ent_type == MEDIA_ENT_T_DEVNODE) atomic_set(&fimc->out_path, FIMC_IO_DMA); else ret = -EINVAL; break; case FLITE_SD_PAD_SOURCE_ISP: if (!(flags & MEDIA_LNK_FL_ENABLED)) atomic_set(&fimc->out_path, FIMC_IO_NONE); else if (remote_ent_type == MEDIA_ENT_T_V4L2_SUBDEV) atomic_set(&fimc->out_path, FIMC_IO_ISP); else ret = -EINVAL; break; default: v4l2_err(sd, "Invalid pad index\n"); ret = -EINVAL; } mb(); return ret; }