aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMauro Carvalho Chehab <mchehab@redhat.com>2010-04-06 22:21:46 -0400
committerMauro Carvalho Chehab <mchehab@redhat.com>2010-05-19 11:57:02 -0400
commit626cf6979e99bf2c642456308bed7bb25a37569b (patch)
tree4a5654588a37399f9240639d75064901c8737d8c
parentde88f31cef8fee7c890cf2128bec8dae06bb20f2 (diff)
V4L/DVB: ir-core: Distinguish sysfs attributes for in-hardware and raw decoders
Some devices have in-hardware Remote Controller decoder, while others need a software decoder to get the IR code. As each software decoder can be enabled/disabled individually, allowing multiple protocol decoding capability. On the other hand, hardware decoders have a limited protocol support, often being able of decoding just one protocol each time. So, each type needs a different set of capabilities to control the supported protocol(s). Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
-rw-r--r--drivers/media/IR/ir-keytable.c17
-rw-r--r--drivers/media/IR/ir-raw-event.c2
-rw-r--r--drivers/media/IR/ir-sysfs.c25
-rw-r--r--drivers/media/video/saa7134/saa7134-input.c9
-rw-r--r--include/media/ir-core.h20
5 files changed, 47 insertions, 26 deletions
diff --git a/drivers/media/IR/ir-keytable.c b/drivers/media/IR/ir-keytable.c
index af7400bc906f..1fdb528737fe 100644
--- a/drivers/media/IR/ir-keytable.c
+++ b/drivers/media/IR/ir-keytable.c
@@ -488,11 +488,19 @@ int __ir_input_register(struct input_dev *input_dev,
488 if (rc < 0) 488 if (rc < 0)
489 goto out_table; 489 goto out_table;
490 490
491 if (ir_dev->props->driver_type == RC_DRIVER_IR_RAW) {
492 rc = ir_raw_event_register(input_dev);
493 if (rc < 0)
494 goto out_event;
495 }
496
491 IR_dprintk(1, "Registered input device on %s for %s remote.\n", 497 IR_dprintk(1, "Registered input device on %s for %s remote.\n",
492 driver_name, rc_tab->name); 498 driver_name, rc_tab->name);
493 499
494 return 0; 500 return 0;
495 501
502out_event:
503 ir_unregister_class(input_dev);
496out_table: 504out_table:
497 kfree(ir_dev->rc_tab.scan); 505 kfree(ir_dev->rc_tab.scan);
498out_name: 506out_name:
@@ -509,22 +517,25 @@ EXPORT_SYMBOL_GPL(__ir_input_register);
509 517
510 * This routine is used to free memory and de-register interfaces. 518 * This routine is used to free memory and de-register interfaces.
511 */ 519 */
512void ir_input_unregister(struct input_dev *dev) 520void ir_input_unregister(struct input_dev *input_dev)
513{ 521{
514 struct ir_input_dev *ir_dev = input_get_drvdata(dev); 522 struct ir_input_dev *ir_dev = input_get_drvdata(input_dev);
515 struct ir_scancode_table *rc_tab; 523 struct ir_scancode_table *rc_tab;
516 524
517 if (!ir_dev) 525 if (!ir_dev)
518 return; 526 return;
519 527
520 IR_dprintk(1, "Freed keycode table\n"); 528 IR_dprintk(1, "Freed keycode table\n");
529
521 del_timer_sync(&ir_dev->timer_keyup); 530 del_timer_sync(&ir_dev->timer_keyup);
531 if (ir_dev->props->driver_type == RC_DRIVER_IR_RAW)
532 ir_raw_event_unregister(input_dev);
522 rc_tab = &ir_dev->rc_tab; 533 rc_tab = &ir_dev->rc_tab;
523 rc_tab->size = 0; 534 rc_tab->size = 0;
524 kfree(rc_tab->scan); 535 kfree(rc_tab->scan);
525 rc_tab->scan = NULL; 536 rc_tab->scan = NULL;
526 537
527 ir_unregister_class(dev); 538 ir_unregister_class(input_dev);
528 539
529 kfree(ir_dev->driver_name); 540 kfree(ir_dev->driver_name);
530 kfree(ir_dev); 541 kfree(ir_dev);
diff --git a/drivers/media/IR/ir-raw-event.c b/drivers/media/IR/ir-raw-event.c
index ddb3365adc82..bc4ca08adf4a 100644
--- a/drivers/media/IR/ir-raw-event.c
+++ b/drivers/media/IR/ir-raw-event.c
@@ -82,7 +82,6 @@ int ir_raw_event_register(struct input_dev *input_dev)
82 82
83 return rc; 83 return rc;
84} 84}
85EXPORT_SYMBOL_GPL(ir_raw_event_register);
86 85
87void ir_raw_event_unregister(struct input_dev *input_dev) 86void ir_raw_event_unregister(struct input_dev *input_dev)
88{ 87{
@@ -97,7 +96,6 @@ void ir_raw_event_unregister(struct input_dev *input_dev)
97 kfree(ir->raw); 96 kfree(ir->raw);
98 ir->raw = NULL; 97 ir->raw = NULL;
99} 98}
100EXPORT_SYMBOL_GPL(ir_raw_event_unregister);
101 99
102int ir_raw_event_store(struct input_dev *input_dev, enum raw_event_type type) 100int ir_raw_event_store(struct input_dev *input_dev, enum raw_event_type type)
103{ 101{
diff --git a/drivers/media/IR/ir-sysfs.c b/drivers/media/IR/ir-sysfs.c
index c33333f1f60e..81eebd8eae5a 100644
--- a/drivers/media/IR/ir-sysfs.c
+++ b/drivers/media/IR/ir-sysfs.c
@@ -152,22 +152,26 @@ static int ir_dev_uevent(struct device *device, struct kobj_uevent_env *env)
152static DEVICE_ATTR(current_protocol, S_IRUGO | S_IWUSR, 152static DEVICE_ATTR(current_protocol, S_IRUGO | S_IWUSR,
153 show_protocol, store_protocol); 153 show_protocol, store_protocol);
154 154
155static struct attribute *ir_dev_attrs[] = { 155static struct attribute *ir_hw_dev_attrs[] = {
156 &dev_attr_current_protocol.attr, 156 &dev_attr_current_protocol.attr,
157 NULL, 157 NULL,
158}; 158};
159 159
160static struct attribute_group ir_dev_attr_grp = { 160static struct attribute_group ir_hw_dev_attr_grp = {
161 .attrs = ir_dev_attrs, 161 .attrs = ir_hw_dev_attrs,
162}; 162};
163 163
164static const struct attribute_group *ir_dev_attr_groups[] = { 164static const struct attribute_group *ir_hw_dev_attr_groups[] = {
165 &ir_dev_attr_grp, 165 &ir_hw_dev_attr_grp,
166 NULL 166 NULL
167}; 167};
168 168
169static struct device_type ir_dev_type = { 169static struct device_type rc_dev_type = {
170 .groups = ir_dev_attr_groups, 170 .groups = ir_hw_dev_attr_groups,
171 .uevent = ir_dev_uevent,
172};
173
174static struct device_type ir_raw_dev_type = {
171 .uevent = ir_dev_uevent, 175 .uevent = ir_dev_uevent,
172}; 176};
173 177
@@ -181,7 +185,6 @@ int ir_register_class(struct input_dev *input_dev)
181{ 185{
182 int rc; 186 int rc;
183 const char *path; 187 const char *path;
184
185 struct ir_input_dev *ir_dev = input_get_drvdata(input_dev); 188 struct ir_input_dev *ir_dev = input_get_drvdata(input_dev);
186 int devno = find_first_zero_bit(&ir_core_dev_number, 189 int devno = find_first_zero_bit(&ir_core_dev_number,
187 IRRCV_NUM_DEVICES); 190 IRRCV_NUM_DEVICES);
@@ -189,7 +192,11 @@ int ir_register_class(struct input_dev *input_dev)
189 if (unlikely(devno < 0)) 192 if (unlikely(devno < 0))
190 return devno; 193 return devno;
191 194
192 ir_dev->dev.type = &ir_dev_type; 195 if (ir_dev->props->driver_type == RC_DRIVER_SCANCODE)
196 ir_dev->dev.type = &rc_dev_type;
197 else
198 ir_dev->dev.type = &ir_raw_dev_type;
199
193 ir_dev->dev.class = &ir_input_class; 200 ir_dev->dev.class = &ir_input_class;
194 ir_dev->dev.parent = input_dev->dev.parent; 201 ir_dev->dev.parent = input_dev->dev.parent;
195 dev_set_name(&ir_dev->dev, "rc%d", devno); 202 dev_set_name(&ir_dev->dev, "rc%d", devno);
diff --git a/drivers/media/video/saa7134/saa7134-input.c b/drivers/media/video/saa7134/saa7134-input.c
index 867f027c3feb..6d5fe596245d 100644
--- a/drivers/media/video/saa7134/saa7134-input.c
+++ b/drivers/media/video/saa7134/saa7134-input.c
@@ -855,6 +855,9 @@ int saa7134_input_init1(struct saa7134_dev *dev)
855 ir->props.open = saa7134_ir_open; 855 ir->props.open = saa7134_ir_open;
856 ir->props.close = saa7134_ir_close; 856 ir->props.close = saa7134_ir_close;
857 857
858 if (raw_decode)
859 ir->props.driver_type = RC_DRIVER_IR_RAW;
860
858 if (!raw_decode && allow_protocol_change) { 861 if (!raw_decode && allow_protocol_change) {
859 ir->props.allowed_protos = IR_TYPE_RC5 | IR_TYPE_NEC; 862 ir->props.allowed_protos = IR_TYPE_RC5 | IR_TYPE_NEC;
860 ir->props.change_protocol = saa7134_ir_change_protocol; 863 ir->props.change_protocol = saa7134_ir_change_protocol;
@@ -880,11 +883,6 @@ int saa7134_input_init1(struct saa7134_dev *dev)
880 err = ir_input_register(ir->dev, ir_codes, &ir->props, MODULE_NAME); 883 err = ir_input_register(ir->dev, ir_codes, &ir->props, MODULE_NAME);
881 if (err) 884 if (err)
882 goto err_out_free; 885 goto err_out_free;
883 if (raw_decode) {
884 err = ir_raw_event_register(ir->dev);
885 if (err)
886 goto err_out_free;
887 }
888 886
889 /* the remote isn't as bouncy as a keyboard */ 887 /* the remote isn't as bouncy as a keyboard */
890 ir->dev->rep[REP_DELAY] = repeat_delay; 888 ir->dev->rep[REP_DELAY] = repeat_delay;
@@ -904,7 +902,6 @@ void saa7134_input_fini(struct saa7134_dev *dev)
904 return; 902 return;
905 903
906 saa7134_ir_stop(dev); 904 saa7134_ir_stop(dev);
907 ir_raw_event_unregister(dev->remote->dev);
908 ir_input_unregister(dev->remote->dev); 905 ir_input_unregister(dev->remote->dev);
909 kfree(dev->remote); 906 kfree(dev->remote);
910 dev->remote = NULL; 907 dev->remote = NULL;
diff --git a/include/media/ir-core.h b/include/media/ir-core.h
index 4397ea3d9754..e9fa94fe2ef5 100644
--- a/include/media/ir-core.h
+++ b/include/media/ir-core.h
@@ -26,6 +26,11 @@ extern int ir_core_debug;
26#define IR_dprintk(level, fmt, arg...) if (ir_core_debug >= level) \ 26#define IR_dprintk(level, fmt, arg...) if (ir_core_debug >= level) \
27 printk(KERN_DEBUG "%s: " fmt , __func__, ## arg) 27 printk(KERN_DEBUG "%s: " fmt , __func__, ## arg)
28 28
29enum rc_driver_type {
30 RC_DRIVER_SCANCODE = 0, /* Driver or hardware generates a scancode */
31 RC_DRIVER_IR_RAW, /* Needs a Infra-Red pulse/space decoder */
32};
33
29enum raw_event_type { 34enum raw_event_type {
30 IR_SPACE = (1 << 0), 35 IR_SPACE = (1 << 0),
31 IR_PULSE = (1 << 1), 36 IR_PULSE = (1 << 1),
@@ -35,6 +40,8 @@ enum raw_event_type {
35 40
36/** 41/**
37 * struct ir_dev_props - Allow caller drivers to set special properties 42 * struct ir_dev_props - Allow caller drivers to set special properties
43 * @driver_type: specifies if the driver or hardware have already a decoder,
44 * or if it needs to use the IR raw event decoders to produce a scancode
38 * @allowed_protos: bitmask with the supported IR_TYPE_* protocols 45 * @allowed_protos: bitmask with the supported IR_TYPE_* protocols
39 * @scanmask: some hardware decoders are not capable of providing the full 46 * @scanmask: some hardware decoders are not capable of providing the full
40 * scancode to the application. As this is a hardware limit, we can't do 47 * scancode to the application. As this is a hardware limit, we can't do
@@ -49,12 +56,13 @@ enum raw_event_type {
49 * is opened. 56 * is opened.
50 */ 57 */
51struct ir_dev_props { 58struct ir_dev_props {
52 unsigned long allowed_protos; 59 enum rc_driver_type driver_type;
53 u32 scanmask; 60 unsigned long allowed_protos;
54 void *priv; 61 u32 scanmask;
55 int (*change_protocol)(void *priv, u64 ir_type); 62 void *priv;
56 int (*open)(void *priv); 63 int (*change_protocol)(void *priv, u64 ir_type);
57 void (*close)(void *priv); 64 int (*open)(void *priv);
65 void (*close)(void *priv);
58}; 66};
59 67
60struct ir_raw_event { 68struct ir_raw_event {