Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 249845
b: refs/heads/master
c: 1f78568
h: refs/heads/master
i:
  249843: 9acdd7a
v: v3
  • Loading branch information
Jonathan Cameron authored and Greg Kroah-Hartman committed May 19, 2011
1 parent f952d6e commit 4de3edb
Show file tree
Hide file tree
Showing 4 changed files with 150 additions and 36 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 586d15255dd529be94253b2d4bbb9f40ef680c1a
refs/heads/master: 1f785681a87068f123d3e23da13b2c55ab4f93ac
13 changes: 13 additions & 0 deletions trunk/drivers/staging/iio/industrialio-trigger.c
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,19 @@ irqreturn_t iio_trigger_generic_data_rdy_poll(int irq, void *private)
}
EXPORT_SYMBOL(iio_trigger_generic_data_rdy_poll);

void iio_trigger_poll_chained(struct iio_trigger *trig, s64 time)
{
int i;
if (!trig->use_count) {
for (i = 0; i < CONFIG_IIO_CONSUMERS_PER_TRIGGER; i++)
if (trig->subirqs[i].enabled) {
trig->use_count++;
handle_nested_irq(trig->subirq_base + i);
}
}
}
EXPORT_SYMBOL(iio_trigger_poll_chained);

void iio_trigger_notify_done(struct iio_trigger *trig)
{
trig->use_count--;
Expand Down
1 change: 1 addition & 0 deletions trunk/drivers/staging/iio/trigger.h
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,7 @@ int iio_trigger_dettach_poll_func(struct iio_trigger *trig,
* Typically called in relevant hardware interrupt handler.
**/
void iio_trigger_poll(struct iio_trigger *trig, s64 time);
void iio_trigger_poll_chained(struct iio_trigger *trig, s64 time);
void iio_trigger_notify_done(struct iio_trigger *trig);

irqreturn_t iio_trigger_generic_data_rdy_poll(int irq, void *private);
Expand Down
170 changes: 135 additions & 35 deletions trunk/drivers/staging/iio/trigger/iio-trig-sysfs.c
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,84 @@
#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/slab.h>
#include <linux/list.h>

#include "../iio.h"
#include "../trigger.h"

struct iio_sysfs_trig {
struct iio_trigger *trig;
int id;
struct list_head l;
};

static LIST_HEAD(iio_sysfs_trig_list);
static DEFINE_MUTEX(iio_syfs_trig_list_mut);

static int iio_sysfs_trigger_probe(int id);
static ssize_t iio_sysfs_trig_add(struct device *dev,
struct device_attribute *attr,
const char *buf,
size_t len)
{
int ret;
unsigned long input;

ret = strict_strtoul(buf, 10, &input);
if (ret)
return ret;
ret = iio_sysfs_trigger_probe(input);
if (ret)
return ret;
return len;
}
static DEVICE_ATTR(add_trigger, S_IWUSR, NULL, &iio_sysfs_trig_add);

static int iio_sysfs_trigger_remove(int id);
static ssize_t iio_sysfs_trig_remove(struct device *dev,
struct device_attribute *attr,
const char *buf,
size_t len)
{
int ret;
unsigned long input;

ret = strict_strtoul(buf, 10, &input);
if (ret)
return ret;
ret = iio_sysfs_trigger_remove(input);
if (ret)
return ret;
return len;
}

static DEVICE_ATTR(remove_trigger, S_IWUSR, NULL, &iio_sysfs_trig_remove);

static struct attribute *iio_sysfs_trig_attrs[] = {
&dev_attr_add_trigger.attr,
&dev_attr_remove_trigger.attr,
NULL,
};

static const struct attribute_group iio_sysfs_trig_group = {
.attrs = iio_sysfs_trig_attrs,
};

static const struct attribute_group *iio_sysfs_trig_groups[] = {
&iio_sysfs_trig_group,
NULL
};

static struct device iio_sysfs_trig_dev = {
.bus = &iio_bus_type,
.groups = iio_sysfs_trig_groups,
};

static ssize_t iio_sysfs_trigger_poll(struct device *dev,
struct device_attribute *attr, const char *buf, size_t count)
{
struct iio_trigger *trig = dev_get_drvdata(dev);
iio_trigger_poll(trig, 0);
iio_trigger_poll_chained(trig, 0);

return count;
}
Expand All @@ -35,70 +104,101 @@ static const struct attribute_group iio_sysfs_trigger_attr_group = {
.attrs = iio_sysfs_trigger_attrs,
};

static int __devinit iio_sysfs_trigger_probe(struct platform_device *pdev)
static int iio_sysfs_trigger_probe(int id)
{
struct iio_trigger *trig;
struct iio_sysfs_trig *t;
int ret;
char *name;
bool foundit = false;
mutex_lock(&iio_syfs_trig_list_mut);
list_for_each_entry(t, &iio_sysfs_trig_list, l)
if (id == t->id) {
foundit = true;
break;
}
if (foundit) {
ret = -EINVAL;
goto out1;
}

trig = iio_allocate_trigger();
if (!trig) {
name = kasprintf(GFP_KERNEL, "sysfstrig%d", id);
if (name == NULL) {
ret = -ENOMEM;
goto out1;
}

trig->control_attrs = &iio_sysfs_trigger_attr_group;
trig->owner = THIS_MODULE;
trig->name = kasprintf(GFP_KERNEL, "sysfstrig%d", pdev->id);
if (trig->name == NULL) {
t = kmalloc(sizeof(*t), GFP_KERNEL);
if (t == NULL) {
ret = -ENOMEM;
goto out2;
goto free_name;
}
t->id = id;
t->trig = iio_allocate_trigger_named(name);
if (!t->trig) {
ret = -ENOMEM;
goto free_t;
}

ret = iio_trigger_register(trig);
if (ret)
goto out3;

platform_set_drvdata(pdev, trig);
t->trig->control_attrs = &iio_sysfs_trigger_attr_group;
t->trig->owner = THIS_MODULE;
t->trig->dev.parent = &iio_sysfs_trig_dev;

ret = iio_trigger_register(t->trig);
if (ret)
goto out2;
list_add(&t->l, &iio_sysfs_trig_list);
__module_get(THIS_MODULE);
mutex_unlock(&iio_syfs_trig_list_mut);
return 0;
out3:
kfree(trig->name);

out2:
iio_put_trigger(trig);
iio_put_trigger(t->trig);
free_t:
kfree(t);
free_name:
kfree(name);
out1:

mutex_unlock(&iio_syfs_trig_list_mut);
return ret;
}

static int __devexit iio_sysfs_trigger_remove(struct platform_device *pdev)
static int iio_sysfs_trigger_remove(int id)
{
struct iio_trigger *trig = platform_get_drvdata(pdev);
bool foundit = false;
struct iio_sysfs_trig *t;
mutex_lock(&iio_syfs_trig_list_mut);
list_for_each_entry(t, &iio_sysfs_trig_list, l)
if (id == t->id) {
foundit = true;
break;
}
if (!foundit) {
mutex_unlock(&iio_syfs_trig_list_mut);
return -EINVAL;
}

iio_trigger_unregister(trig);
kfree(trig->name);
iio_put_trigger(trig);
iio_trigger_unregister(t->trig);
kfree(t->trig->name);
iio_free_trigger(t->trig);

list_del(&t->l);
kfree(t);
module_put(THIS_MODULE);
mutex_unlock(&iio_syfs_trig_list_mut);
return 0;
}

static struct platform_driver iio_sysfs_trigger_driver = {
.driver = {
.name = "iio_sysfs_trigger",
.owner = THIS_MODULE,
},
.probe = iio_sysfs_trigger_probe,
.remove = __devexit_p(iio_sysfs_trigger_remove),
};

static int __init iio_sysfs_trig_init(void)
{
return platform_driver_register(&iio_sysfs_trigger_driver);
device_initialize(&iio_sysfs_trig_dev);
dev_set_name(&iio_sysfs_trig_dev, "iio_sysfs_trigger");
return device_add(&iio_sysfs_trig_dev);
}
module_init(iio_sysfs_trig_init);

static void __exit iio_sysfs_trig_exit(void)
{
platform_driver_unregister(&iio_sysfs_trigger_driver);
device_unregister(&iio_sysfs_trig_dev);
}
module_exit(iio_sysfs_trig_exit);

Expand Down

0 comments on commit 4de3edb

Please sign in to comment.