Re: [PATCH] isl6421.c - added optional features: tone control and temporary diseqc overcurrent

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

 



Hi Mauro,

thank you for your valued hints. I'm commenting inside
message:

> First of all, please check all your patches with checkpatch, to be sure
> that they don't have any CodingStyle troubles. There are some on your
> patch (the better is to read README.patches for more info useful
> for developers).

Did checkpatch testing and has fixed all errors/warnings except
of 3 warning regarding longer line (all 3 lines has exactly
one char over 80, so I guess it should not bother much).
Of course if this rule is a must, then I can fix that also).

>>
>> Attached patch adds two optional (so, disabled by default
>> and therefore could not break any compatibility) features:
>>
>> 1, tone_control=1
>> When enabled, ISL6421 overrides frontend's tone control
>> function (fe->ops.set_tone) by its own one.
>>
>
> On your comments, the better is to describe why someone would need
> to use such option. You should also add a quick hint about that at the
> option description.

Well, I'm not sure I can make some good hint why such option can
be useful by someone. I can only say that isl6121 has possibility
to drive 22k tone, so why not enable usage of it?

Of course, we made such code because we were using exactly
this way of 22k control in our device.

>>
>> 2, overcurrent_enable=1
>> When enabled, overcurrent protection is disabled during
>> sending diseqc command. Such option is usable when ISL6421
>> catch overcurrent threshold and starts limiting output.
>> Note: protection is disabled only during sending
>> of diseqc command, until next set_tone() usage.
>> What typically means only max up to few hundreds of ms.
>> WARNING: overcurrent_enable=1 is dangerous
>> and can damage your device. Use with care
>> and only if you really know what you do.
>>
>
> I'm not sure if it is a good idea to have this... Why/when someone would
> need this?
>

I know that it is a bit dangerous option, so I can understand you can
don't like it :)

But I would like to note again - such way of using is permitted
by datasheet (otherwise it would not be even possible to enable it)
and we learnt when used correctly (it is enabled only within diseqc
sequence), it boost rotor moving or fixes using some "power-eating"
diseqc switches.

If you still feel it is better to not support bit strange mode, then
I can live with "#if 0" commented out blocks or adding some
kernel config option with something like ISL6421_ENABLE_OVERCURRENT
or so.

> If we go ahead and add this one, you should add a notice about it at the
> parameter.
> I would also print a big WARNING message at the dmesg if the module were
> loaded
> with this option turned on.

Added some WARNING printing to dmesg when option is enabled.

Regards

/Honza

---

Signed-off-by: Jan Petrous <jpetrous@xxxxxxxxx>
Signed-off-by: Ales Jurik <ajurik@xxxxxxxx>
diff -r 9d9bc92d7c33 drivers/media/dvb/frontends/isl6421.c
--- a/drivers/media/dvb/frontends/isl6421.c	Sat Sep 19 12:48:44 2009 +0200
+++ b/drivers/media/dvb/frontends/isl6421.c	Tue Nov 03 23:23:05 2009 +0100
@@ -3,6 +3,9 @@
  *
  * Copyright (C) 2006 Andrew de Quincey
  * Copyright (C) 2006 Oliver Endriss
+ * Copyright (C) 2009 Ales Jurik and Jan Petrous (added optional 22k tone
+ *                    support and temporary diseqc overcurrent enable until
+ *                    next command - set voltage or tone)
  *
  * This program is free software; you can redistribute it and/or
  * modify it under the terms of the GNU General Public License
@@ -35,12 +38,23 @@
 #include "dvb_frontend.h"
 #include "isl6421.h"
 
+static int tone_control;
+module_param(tone_control, int, S_IRUGO);
+MODULE_PARM_DESC(tone_control, "Set ISL6421 to control 22kHz tone");
+
+static int overcurrent_enable;
+module_param(overcurrent_enable, int, S_IRUGO);
+MODULE_PARM_DESC(overcurrent_enable, "Set ISL6421 to temporary enable "
+		"overcurrent when diseqc command is active");
+
 struct isl6421 {
 	u8			config;
 	u8			override_or;
 	u8			override_and;
 	struct i2c_adapter	*i2c;
 	u8			i2c_addr;
+	int (*diseqc_send_master_cmd_orig)(struct dvb_frontend *fe,
+			struct dvb_diseqc_master_cmd *cmd);
 };
 
 static int isl6421_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage)
@@ -60,6 +74,55 @@ static int isl6421_set_voltage(struct dv
 		break;
 	case SEC_VOLTAGE_18:
 		isl6421->config |= (ISL6421_EN1 | ISL6421_VSEL1);
+		break;
+	default:
+		return -EINVAL;
+	};
+
+	isl6421->config |= isl6421->override_or;
+	isl6421->config &= isl6421->override_and;
+
+	return (i2c_transfer(isl6421->i2c, &msg, 1) == 1) ? 0 : -EIO;
+}
+
+static int isl6421_send_diseqc(struct dvb_frontend *fe,
+				struct dvb_diseqc_master_cmd *cmd)
+{
+	struct isl6421 *isl6421 = (struct isl6421 *) fe->sec_priv;
+	struct i2c_msg msg = {	.addr = isl6421->i2c_addr, .flags = 0,
+				.buf = &isl6421->config,
+				.len = sizeof(isl6421->config) };
+
+	isl6421->config |= ISL6421_DCL;
+
+	isl6421->config |= isl6421->override_or;
+	isl6421->config &= isl6421->override_and;
+
+	if (i2c_transfer(isl6421->i2c, &msg, 1) != 1)
+		return -EIO;
+
+	isl6421->config &= ~ISL6421_DCL;
+
+	return isl6421->diseqc_send_master_cmd_orig(fe, cmd);
+}
+
+static int isl6421_set_tone(struct dvb_frontend *fe, fe_sec_tone_mode_t tone)
+{
+	struct isl6421 *isl6421 = (struct isl6421 *) fe->sec_priv;
+	struct i2c_msg msg = {	.addr = isl6421->i2c_addr, .flags = 0,
+				.buf = &isl6421->config,
+				.len = sizeof(isl6421->config) };
+
+	isl6421->config &= ~(ISL6421_ENT1);
+
+	printk(KERN_INFO "%s: %s\n", __func__, ((tone == SEC_TONE_OFF) ?
+				"Off" : "On"));
+
+	switch (tone) {
+	case SEC_TONE_ON:
+		isl6421->config |= ISL6421_ENT1;
+		break;
+	case SEC_TONE_OFF:
 		break;
 	default:
 		return -EINVAL;
@@ -91,18 +154,26 @@ static int isl6421_enable_high_lnb_volta
 
 static void isl6421_release(struct dvb_frontend *fe)
 {
+	struct isl6421 *isl6421 = (struct isl6421 *) fe->sec_priv;
+
 	/* power off */
 	isl6421_set_voltage(fe, SEC_VOLTAGE_OFF);
+
+	if (overcurrent_enable)
+		fe->ops.diseqc_send_master_cmd =
+			isl6421->diseqc_send_master_cmd_orig;
 
 	/* free */
 	kfree(fe->sec_priv);
 	fe->sec_priv = NULL;
 }
 
-struct dvb_frontend *isl6421_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, u8 i2c_addr,
-		   u8 override_set, u8 override_clear)
+struct dvb_frontend *isl6421_attach(struct dvb_frontend *fe,
+		struct i2c_adapter *i2c, u8 i2c_addr, u8 override_set,
+		u8 override_clear)
 {
 	struct isl6421 *isl6421 = kmalloc(sizeof(struct isl6421), GFP_KERNEL);
+
 	if (!isl6421)
 		return NULL;
 
@@ -131,6 +202,33 @@ struct dvb_frontend *isl6421_attach(stru
 	/* override frontend ops */
 	fe->ops.set_voltage = isl6421_set_voltage;
 	fe->ops.enable_high_lnb_voltage = isl6421_enable_high_lnb_voltage;
+	if (tone_control)
+		fe->ops.set_tone = isl6421_set_tone;
+
+	printk(KERN_INFO "ISL6421 attached on addr=%x\n", i2c_addr);
+
+	if (overcurrent_enable) {
+		if ((override_set & ISL6421_DCL) ||
+				(override_clear & ISL6421_DCL)) {
+			/* there is no sense to use overcurrent_enable
+			 * with DCL bit set in any override byte */
+			if (override_set & ISL6421_DCL)
+				printk(KERN_WARNING "ISL6421 overcurrent_enable"
+						" with DCL bit in override_set,"
+						" overcurrent_enable ignored\n");
+			if (override_clear & ISL6421_DCL)
+				printk(KERN_WARNING "ISL6421 overcurrent_enable"
+						" with DCL bit in override_clear,"
+						" overcurrent_enable ignored\n");
+		} else {
+			printk(KERN_WARNING "ISL6421 overcurrent_enable "
+					" activated. WARNING: it can be "
+					" dangerous for your hardware!");
+			isl6421->diseqc_send_master_cmd_orig =
+				fe->ops.diseqc_send_master_cmd;
+			fe->ops.diseqc_send_master_cmd = isl6421_send_diseqc;
+		}
+	}
 
 	return fe;
 }

[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