Re: [PATCH v2 2/2] as3645a: Add driver for LED flash controller

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi Sakari,

On Tuesday 15 November 2011 16:28:06 Sakari Ailus wrote:
> Laurent Pinchart wrote:
> > On Monday 14 November 2011 10:34:57 Sakari Ailus wrote:

[snip]

> >>> +	if (rval & ~AS_FAULT_INFO_INDICATOR_LED)
> >>> +		dev_dbg(&client->dev, "No faults, nice\n");
> >>> +
> >>> +	return rval;
> >>> +}
> >>> +
> >>> +static int as3645a_get_ctrl(struct v4l2_ctrl *ctrl)
> >>> +{
> >>> +	struct as3645a *flash =
> >>> +		container_of(ctrl->handler, struct as3645a, ctrls);
> >>> +	struct i2c_client *client = v4l2_get_subdevdata(&flash->subdev);
> >>> +	int fault;
> >>> +
> >>> +	switch (ctrl->id) {
> >>> +	case V4L2_CID_FLASH_FAULT:
> >>> +		fault = as3645a_read_fault(flash);
> >>> +		if (fault < 0)
> >>> +			return fault;
> >> 
> >> ctrl->cur.val = 0 here?
> > 
> > fault being negative means that reading the fault register failed. In
> > that case I don't think we should update ctrl->cur.val.
> 
> I thought that ctrl->cur.val should be assigned to zero before settings
> bits in it. Does that sound better? :-)

Oops, my bad, I misunderstood your comment. I'll fix that.

> >>> +static int as3645a_registered(struct v4l2_subdev *sd)
> >>> +{
> >>> +	struct as3645a *flash = to_as3645a(sd);
> >>> +	struct i2c_client *client = v4l2_get_subdevdata(sd);
> >>> +	int rval, man, model, rfu, version;
> >>> +	const char *factory;
> >>> +
> >>> +	/* Power up the flash driver and read manufacturer ID, model ID, RFU
> >>> +	 * and version.
> >>> +	 */
> >>> +	as3645a_set_power(&flash->subdev, 1);
> >>> +
> >>> +	rval = as3645a_read(flash, AS_DESIGN_INFO_REG);
> >>> +	if (rval < 0)
> >>> +		goto power_off;
> >>> +
> >>> +	man = AS_DESIGN_INFO_FACTORY(rval);
> >>> +	model = AS_DESIGN_INFO_MODEL(rval);
> >>> +
> >>> +	rval = as3645a_read(flash, AS_VERSION_CONTROL_REG);
> >>> +	if (rval < 0)
> >>> +		goto power_off;
> >>> +
> >>> +	rfu = AS_VERSION_CONTROL_RFU(rval);
> >>> +	version = AS_VERSION_CONTROL_VERSION(rval);
> >>> +
> >>> +	/* Verify the chip model and version. */
> >>> +	if (model != 0x0001 || rfu != 0x0000) {
> >>> +		dev_err(&client->dev, "AS3645A not detected "
> >>> +			"(model %d rfu %d)\n", model, rfu);
> >>> +		rval = -ENODEV;
> >> 
> >> Is this so grave issue we should discontinue? I'd perhaps print a
> >> warning if even that.
> > 
> > This could mean that the chip isn't an AS3645A/LM3555 at all. Many I2C
> > drivers perform the same check, they read the ID register and fail if it
> > doesn't contain the expected value.
> 
> Shouldn't we instead check the design info register has a valid id in it
> only? The spec I have doesn't say anything about the version of the
> chip.

I agree that checking the model shoudl be enough. However, if a new chip comes 
out with an RFU value != 0, it will probably mean that the driver will need to 
be adapted anyway. Isn't it better to catch that instead of ignoring it ?

> I.e. I'd leave the rfu check out. Also, the registers are 8 bit
> wide, with each four fields having four bits in all of them.

[snip]

> >>> +static int as3645a_init_controls(struct as3645a *flash)
> >>> +{
> >>> +	struct as3645a_flash_torch_parms *flash_params = NULL;
> >>> +	bool use_ext_strobe = false;
> >>> +	unsigned int leds = 2;
> >>> +	struct v4l2_ctrl *ctrl;
> >>> +	int minimum;
> >>> +	int maximum;
> >>> +
> >>> +	if (flash->platform_data) {
> >>> +		if (flash->platform_data->num_leds)
> >>> +			leds = flash->platform_data->num_leds;
> >>> +
> >>> +		flash_params = flash->platform_data->flash_torch_limits;
> >>> +		use_ext_strobe = flash->platform_data->use_ext_flash_strobe;
> >>> +	}
> >>> +
> >>> +	v4l2_ctrl_handler_init(&flash->ctrls, 9);
> >>> +
> >>> +	/* V4L2_CID_FLASH_LED_MODE */
> >>> +	v4l2_ctrl_new_std_menu(&flash->ctrls, &as3645a_ctrl_ops,
> >>> +			       V4L2_CID_FLASH_LED_MODE, 2, ~7,
> >>> +			       V4L2_FLASH_LED_MODE_NONE);
> >>> +
> >>> +	/* V4L2_CID_FLASH_STROBE_SOURCE */
> >>> +	v4l2_ctrl_new_std_menu(&flash->ctrls, &as3645a_ctrl_ops,
> >>> +			       V4L2_CID_FLASH_STROBE_SOURCE,
> >>> +			       use_ext_strobe ? 1 : 0, use_ext_strobe ? ~3 : ~1,
> >>> +			       V4L2_FLASH_STROBE_SOURCE_SOFTWARE);
> >>> +
> >>> +	flash->strobe_source = V4L2_FLASH_STROBE_SOURCE_SOFTWARE;
> >>> +
> >>> +	/* V4L2_CID_FLASH_STROBE */
> >>> +	v4l2_ctrl_new_std(&flash->ctrls, &as3645a_ctrl_ops,
> >>> +			  V4L2_CID_FLASH_STROBE, 0, 0, 0, 0);
> >>> +
> >>> +	/* V4L2_CID_FLASH_STROBE_STOP */
> >>> +	v4l2_ctrl_new_std(&flash->ctrls, &as3645a_ctrl_ops,
> >>> +			  V4L2_CID_FLASH_STROBE_STOP, 0, 0, 0, 0);
> >>> +
> >>> +	/* V4L2_CID_FLASH_TIMEOUT */
> >>> +	if (flash_params) {
> >> 
> >> Shouldn't we require valid values for the flash parameters always?
> >> Chances are very high the default ones for the flash controller won't
> >> apply for the LED connected to it.
> > 
> > Good question. If no flash parameters are provided the driver uses the
> > chip's maximum ratings. I'm fine with both.
> 
> I guess that the most common case of nonexistent flash current and
> timeout limits could be just telling they're missing for a reason or
> another, which can be harmful for the hardware. I'd require them.

OK.

> >>> +struct as3645a_platform_data {
> >>> +	int (*set_power)(struct v4l2_subdev *subdev, int on);
> >>> +	/* used to notify the entity which trigger external strobe signal */
> >>> +	void (*setup_ext_strobe)(int enable);
> >>> +	/* Sends the strobe width to the sensor strobe configuration */
> >>> +	void (*set_strobe_width)(u32 width_in_us);
> >> 
> >> I don't think we should have the above two callbacks at all. This should
> >> be controlled from the user space instead.
> > 
> > Should I remove external strobe mode completely then ?
> 
> Not necessarily. I think the control should come from the sensor (or
> whichever component is controlling the external strobe) instead. Another
> question is then how this should interact with the flash temperature
> protection code.

OK, I'll keep external strobe mode.

v4 is on its way.

-- 
Regards,

Laurent Pinchart
--
To unsubscribe from this list: send the line "unsubscribe linux-media" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[Index of Archives]     [Linux Input]     [Video for Linux]     [Gstreamer Embedded]     [Mplayer Users]     [Linux USB Devel]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Yosemite Backpacking]
  Powered by Linux