remove linux 2.4 specific build system code
[15.05/openwrt.git] / target / linux / generic-2.6 / files / drivers / pwm / pwm.c
1 /*
2  * drivers/pwm/pwm.c
3  *
4  * Copyright (C) 2010 Bill Gatliff <bgat@billgatliff.com>
5  *
6  * This program is free software; you may redistribute and/or modify
7  * it under the terms of the GNU General Public License version 2 as
8  * published by the Free Software Foundation.
9  *
10  * This program is distributed in the hope that it will be useful, but
11  * WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
18  * USA
19  */
20
21 #include <linux/kernel.h>
22 #include <linux/module.h>
23 #include <linux/init.h>
24 #include <linux/device.h>
25 #include <linux/spinlock.h>
26 #include <linux/fs.h>
27 #include <linux/completion.h>
28 #include <linux/workqueue.h>
29 #include <linux/list.h>
30 #include <linux/sched.h>
31 #include <linux/slab.h>    /*kcalloc, kfree since 2.6.34 */
32 #include <linux/pwm/pwm.h>
33
34 static int __pwm_create_sysfs(struct pwm_device *pwm);
35
36 static const char *REQUEST_SYSFS = "sysfs";
37 static LIST_HEAD(pwm_device_list);
38 static DEFINE_MUTEX(device_list_mutex);
39 static struct class pwm_class;
40 static struct workqueue_struct *pwm_handler_workqueue;
41
42 int pwm_register(struct pwm_device *pwm)
43 {
44         struct pwm_channel *p;
45         int wchan;
46         int ret;
47
48         spin_lock_init(&pwm->list_lock);
49
50         p = kcalloc(pwm->nchan, sizeof(*p), GFP_KERNEL);
51         if (!p)
52                 return -ENOMEM;
53
54         for (wchan = 0; wchan < pwm->nchan; wchan++) {
55                 spin_lock_init(&p[wchan].lock);
56                 init_completion(&p[wchan].complete);
57                 p[wchan].chan = wchan;
58                 p[wchan].pwm = pwm;
59         }
60
61         pwm->channels = p;
62
63         mutex_lock(&device_list_mutex);
64
65         list_add_tail(&pwm->list, &pwm_device_list);
66         ret = __pwm_create_sysfs(pwm);
67         if (ret) {
68                 mutex_unlock(&device_list_mutex);
69                 goto err_create_sysfs;
70         }
71
72         mutex_unlock(&device_list_mutex);
73
74         dev_info(pwm->dev, "%d channel%s\n", pwm->nchan,
75                  pwm->nchan > 1 ? "s" : "");
76         return 0;
77
78 err_create_sysfs:
79         kfree(p);
80
81         return ret;
82 }
83 EXPORT_SYMBOL(pwm_register);
84
85 static int __match_device(struct device *dev, void *data)
86 {
87         return dev_get_drvdata(dev) == data;
88 }
89
90 int pwm_unregister(struct pwm_device *pwm)
91 {
92         int wchan;
93         struct device *dev;
94
95         mutex_lock(&device_list_mutex);
96
97         for (wchan = 0; wchan < pwm->nchan; wchan++) {
98           if (pwm->channels[wchan].flags & BIT(FLAG_REQUESTED)) {
99                         mutex_unlock(&device_list_mutex);
100                         return -EBUSY;
101                 }
102         }
103
104         for (wchan = 0; wchan < pwm->nchan; wchan++) {
105                 dev = class_find_device(&pwm_class, NULL,
106                                         &pwm->channels[wchan],
107                                         __match_device);
108                 if (dev) {
109                         put_device(dev);
110                         device_unregister(dev);
111                 }
112         }
113
114         kfree(pwm->channels);
115         list_del(&pwm->list);
116         mutex_unlock(&device_list_mutex);
117
118         return 0;
119 }
120 EXPORT_SYMBOL(pwm_unregister);
121
122 static struct pwm_device *
123 __pwm_find_device(const char *bus_id)
124 {
125         struct pwm_device *p;
126
127         list_for_each_entry(p, &pwm_device_list, list) {
128                 if (!strcmp(bus_id, p->bus_id))
129                         return p;
130         }
131         return NULL;
132 }
133
134 static int
135 __pwm_request_channel(struct pwm_channel *p,
136                       const char *requester)
137 {
138         int ret;
139
140         if (test_and_set_bit(FLAG_REQUESTED, &p->flags))
141                 return -EBUSY;
142
143         if (p->pwm->request) {
144                 ret = p->pwm->request(p);
145                 if (ret) {
146                         clear_bit(FLAG_REQUESTED, &p->flags);
147                         return ret;
148                 }
149         }
150
151         p->requester = requester;
152         if (!strcmp(requester, REQUEST_SYSFS))
153                 p->pid = current->pid;
154
155         return 0;
156 }
157
158 struct pwm_channel *
159 pwm_request(const char *bus_id,
160             int chan,
161             const char *requester)
162 {
163         struct pwm_device *p;
164         int ret;
165
166         mutex_lock(&device_list_mutex);
167
168         p = __pwm_find_device(bus_id);
169         if (!p || chan >= p->nchan)
170                 goto err_no_device;
171
172         if (!try_module_get(p->owner))
173                 goto err_module_get_failed;
174
175         ret = __pwm_request_channel(&p->channels[chan], requester);
176         if (ret)
177                 goto err_request_failed;
178
179         mutex_unlock(&device_list_mutex);
180         return &p->channels[chan];
181
182 err_request_failed:
183         module_put(p->owner);
184 err_module_get_failed:
185 err_no_device:
186         mutex_unlock(&device_list_mutex);
187         return NULL;
188 }
189 EXPORT_SYMBOL(pwm_request);
190
191 void pwm_free(struct pwm_channel *p)
192 {
193         mutex_lock(&device_list_mutex);
194
195         if (!test_and_clear_bit(FLAG_REQUESTED, &p->flags))
196                 goto done;
197
198         pwm_stop(p);
199         pwm_unsynchronize(p, NULL);
200         pwm_set_handler(p, NULL, NULL);
201
202         if (p->pwm->free)
203                 p->pwm->free(p);
204         module_put(p->pwm->owner);
205 done:
206         mutex_unlock(&device_list_mutex);
207 }
208 EXPORT_SYMBOL(pwm_free);
209
210 unsigned long pwm_ns_to_ticks(struct pwm_channel *p,
211                               unsigned long nsecs)
212 {
213         unsigned long long ticks;
214
215         ticks = nsecs;
216         ticks *= p->tick_hz;
217         do_div(ticks, 1000000000);
218         return ticks;
219 }
220 EXPORT_SYMBOL(pwm_ns_to_ticks);
221
222 unsigned long pwm_ticks_to_ns(struct pwm_channel *p,
223                               unsigned long ticks)
224 {
225         unsigned long long ns;
226
227         if (!p->tick_hz)
228                 return 0;
229
230         ns = ticks;
231         ns *= 1000000000UL;
232         do_div(ns, p->tick_hz);
233         return ns;
234 }
235 EXPORT_SYMBOL(pwm_ticks_to_ns);
236
237 static void
238 pwm_config_ns_to_ticks(struct pwm_channel *p,
239                        struct pwm_channel_config *c)
240 {
241         if (c->config_mask & PWM_CONFIG_PERIOD_NS) {
242                 c->period_ticks = pwm_ns_to_ticks(p, c->period_ns);
243                 c->config_mask &= ~PWM_CONFIG_PERIOD_NS;
244                 c->config_mask |= PWM_CONFIG_PERIOD_TICKS;
245         }
246
247         if (c->config_mask & PWM_CONFIG_DUTY_NS) {
248                 c->duty_ticks = pwm_ns_to_ticks(p, c->duty_ns);
249                 c->config_mask &= ~PWM_CONFIG_DUTY_NS;
250                 c->config_mask |= PWM_CONFIG_DUTY_TICKS;
251         }
252 }
253
254 static void
255 pwm_config_percent_to_ticks(struct pwm_channel *p,
256                             struct pwm_channel_config *c)
257 {
258         if (c->config_mask & PWM_CONFIG_DUTY_PERCENT) {
259                 if (c->config_mask & PWM_CONFIG_PERIOD_TICKS)
260                         c->duty_ticks = c->period_ticks;
261                 else
262                         c->duty_ticks = p->period_ticks;
263
264                 c->duty_ticks *= c->duty_percent;
265                 c->duty_ticks /= 100;
266                 c->config_mask &= ~PWM_CONFIG_DUTY_PERCENT;
267                 c->config_mask |= PWM_CONFIG_DUTY_TICKS;
268         }
269 }
270
271 int pwm_config_nosleep(struct pwm_channel *p,
272                        struct pwm_channel_config *c)
273 {
274         if (!p->pwm->config_nosleep)
275                 return -EINVAL;
276
277         pwm_config_ns_to_ticks(p, c);
278         pwm_config_percent_to_ticks(p, c);
279
280         return p->pwm->config_nosleep(p, c);
281 }
282 EXPORT_SYMBOL(pwm_config_nosleep);
283
284 int pwm_config(struct pwm_channel *p,
285                struct pwm_channel_config *c)
286 {
287         int ret = 0;
288
289         if (unlikely(!p->pwm->config))
290                 return -EINVAL;
291
292         pwm_config_ns_to_ticks(p, c);
293         pwm_config_percent_to_ticks(p, c);
294
295         switch (c->config_mask & (PWM_CONFIG_PERIOD_TICKS
296                                   | PWM_CONFIG_DUTY_TICKS)) {
297         case PWM_CONFIG_PERIOD_TICKS:
298                 if (p->duty_ticks > c->period_ticks) {
299                         ret = -EINVAL;
300                         goto err;
301                 }
302                 break;
303         case PWM_CONFIG_DUTY_TICKS:
304                 if (p->period_ticks < c->duty_ticks) {
305                         ret = -EINVAL;
306                         goto err;
307                 }
308                 break;
309         case PWM_CONFIG_DUTY_TICKS | PWM_CONFIG_PERIOD_TICKS:
310                 if (c->duty_ticks > c->period_ticks) {
311                         ret = -EINVAL;
312                         goto err;
313                 }
314                 break;
315         default:
316                 break;
317         }
318
319 err:
320         dev_dbg(p->pwm->dev, "%s: config_mask %d period_ticks %lu duty_ticks %lu"
321                 " polarity %d duty_ns %lu period_ns %lu duty_percent %d\n",
322                 __func__, c->config_mask, c->period_ticks, c->duty_ticks,
323                 c->polarity, c->duty_ns, c->period_ns, c->duty_percent);
324
325         if (ret)
326                 return ret;
327         return p->pwm->config(p, c);
328 }
329 EXPORT_SYMBOL(pwm_config);
330
331 int pwm_set_period_ns(struct pwm_channel *p,
332                       unsigned long period_ns)
333 {
334         struct pwm_channel_config c = {
335                 .config_mask = PWM_CONFIG_PERIOD_TICKS,
336                 .period_ticks = pwm_ns_to_ticks(p, period_ns),
337         };
338
339         return pwm_config(p, &c);
340 }
341 EXPORT_SYMBOL(pwm_set_period_ns);
342
343 unsigned long pwm_get_period_ns(struct pwm_channel *p)
344 {
345         return pwm_ticks_to_ns(p, p->period_ticks);
346 }
347 EXPORT_SYMBOL(pwm_get_period_ns);
348
349 int pwm_set_duty_ns(struct pwm_channel *p,
350                     unsigned long duty_ns)
351 {
352         struct pwm_channel_config c = {
353                 .config_mask = PWM_CONFIG_DUTY_TICKS,
354                 .duty_ticks = pwm_ns_to_ticks(p, duty_ns),
355         };
356         return pwm_config(p, &c);
357 }
358 EXPORT_SYMBOL(pwm_set_duty_ns);
359
360 unsigned long pwm_get_duty_ns(struct pwm_channel *p)
361 {
362         return pwm_ticks_to_ns(p, p->duty_ticks);
363 }
364 EXPORT_SYMBOL(pwm_get_duty_ns);
365
366 int pwm_set_duty_percent(struct pwm_channel *p,
367                          int percent)
368 {
369         struct pwm_channel_config c = {
370                 .config_mask = PWM_CONFIG_DUTY_PERCENT,
371                 .duty_percent = percent,
372         };
373         return pwm_config(p, &c);
374 }
375 EXPORT_SYMBOL(pwm_set_duty_percent);
376
377 int pwm_set_polarity(struct pwm_channel *p,
378                      int active_high)
379 {
380         struct pwm_channel_config c = {
381                 .config_mask = PWM_CONFIG_POLARITY,
382                 .polarity = active_high,
383         };
384         return pwm_config(p, &c);
385 }
386 EXPORT_SYMBOL(pwm_set_polarity);
387
388 int pwm_start(struct pwm_channel *p)
389 {
390         struct pwm_channel_config c = {
391                 .config_mask = PWM_CONFIG_START,
392         };
393         return pwm_config(p, &c);
394 }
395 EXPORT_SYMBOL(pwm_start);
396
397 int pwm_stop(struct pwm_channel *p)
398 {
399         struct pwm_channel_config c = {
400                 .config_mask = PWM_CONFIG_STOP,
401         };
402         return pwm_config(p, &c);
403 }
404 EXPORT_SYMBOL(pwm_stop);
405
406 int pwm_synchronize(struct pwm_channel *p,
407                     struct pwm_channel *to_p)
408 {
409         if (p->pwm != to_p->pwm) {
410                 /* TODO: support cross-device synchronization */
411                 return -EINVAL;
412         }
413
414         if (!p->pwm->synchronize)
415                 return -EINVAL;
416
417         return p->pwm->synchronize(p, to_p);
418 }
419 EXPORT_SYMBOL(pwm_synchronize);
420
421 int pwm_unsynchronize(struct pwm_channel *p,
422                       struct pwm_channel *from_p)
423 {
424         if (from_p && (p->pwm != from_p->pwm)) {
425                 /* TODO: support cross-device synchronization */
426                 return -EINVAL;
427         }
428
429         if (!p->pwm->unsynchronize)
430                 return -EINVAL;
431
432         return p->pwm->unsynchronize(p, from_p);
433 }
434 EXPORT_SYMBOL(pwm_unsynchronize);
435
436 static void pwm_handler(struct work_struct *w)
437 {
438         struct pwm_channel *p = container_of(w, struct pwm_channel,
439                                              handler_work);
440         if (p->handler && p->handler(p, p->handler_data))
441                 pwm_stop(p);
442 }
443
444 static void __pwm_callback(struct pwm_channel *p)
445 {
446         queue_work(pwm_handler_workqueue, &p->handler_work);
447         dev_dbg(p->pwm->dev, "handler %p scheduled with data %p\n",
448                 p->handler, p->handler_data);
449 }
450
451 int pwm_set_handler(struct pwm_channel *p,
452                     pwm_handler_t handler,
453                     void *data)
454 {
455         if (p->pwm->set_callback) {
456                 p->handler_data = data;
457                 p->handler = handler;
458                 INIT_WORK(&p->handler_work, pwm_handler);
459                 return p->pwm->set_callback(p, handler ? __pwm_callback : NULL);
460         }
461         return -EINVAL;
462 }
463 EXPORT_SYMBOL(pwm_set_handler);
464
465 static ssize_t pwm_run_store(struct device *dev,
466                              struct device_attribute *attr,
467                              const char *buf,
468                              size_t len)
469 {
470         struct pwm_channel *p = dev_get_drvdata(dev);
471         if (sysfs_streq(buf, "1"))
472                 pwm_start(p);
473         else if (sysfs_streq(buf, "0"))
474                 pwm_stop(p);
475         return len;
476 }
477 static DEVICE_ATTR(run, 0200, NULL, pwm_run_store);
478
479 static ssize_t pwm_duty_ns_show(struct device *dev,
480                                 struct device_attribute *attr,
481                                 char *buf)
482 {
483         struct pwm_channel *p = dev_get_drvdata(dev);
484         return sprintf(buf, "%lu\n", pwm_get_duty_ns(p));
485 }
486
487 static ssize_t pwm_duty_ns_store(struct device *dev,
488                                  struct device_attribute *attr,
489                                  const char *buf,
490                                  size_t len)
491 {
492         unsigned long duty_ns;
493         struct pwm_channel *p = dev_get_drvdata(dev);
494
495         if (1 == sscanf(buf, "%lu", &duty_ns))
496                 pwm_set_duty_ns(p, duty_ns);
497         return len;
498 }
499 static DEVICE_ATTR(duty_ns, 0644, pwm_duty_ns_show, pwm_duty_ns_store);
500
501 static ssize_t pwm_period_ns_show(struct device *dev,
502                                   struct device_attribute *attr,
503                                   char *buf)
504 {
505         struct pwm_channel *p = dev_get_drvdata(dev);
506         return sprintf(buf, "%lu\n", pwm_get_period_ns(p));
507 }
508
509 static ssize_t pwm_period_ns_store(struct device *dev,
510                                    struct device_attribute *attr,
511                                    const char *buf,
512                                    size_t len)
513 {
514         unsigned long period_ns;
515         struct pwm_channel *p = dev_get_drvdata(dev);
516
517         if (1 == sscanf(buf, "%lu", &period_ns))
518                 pwm_set_period_ns(p, period_ns);
519         return len;
520 }
521 static DEVICE_ATTR(period_ns, 0644, pwm_period_ns_show, pwm_period_ns_store);
522
523 static ssize_t pwm_polarity_show(struct device *dev,
524                                  struct device_attribute *attr,
525                                  char *buf)
526 {
527         struct pwm_channel *p = dev_get_drvdata(dev);
528         return sprintf(buf, "%d\n", p->active_high ? 1 : 0);
529 }
530
531 static ssize_t pwm_polarity_store(struct device *dev,
532                                   struct device_attribute *attr,
533                                   const char *buf,
534                                   size_t len)
535 {
536         int polarity;
537         struct pwm_channel *p = dev_get_drvdata(dev);
538
539         if (1 == sscanf(buf, "%d", &polarity))
540                 pwm_set_polarity(p, polarity);
541         return len;
542 }
543 static DEVICE_ATTR(polarity, 0644, pwm_polarity_show, pwm_polarity_store);
544
545 static ssize_t pwm_request_show(struct device *dev,
546                                 struct device_attribute *attr,
547                                 char *buf)
548 {
549         struct pwm_channel *p = dev_get_drvdata(dev);
550         mutex_lock(&device_list_mutex);
551         __pwm_request_channel(p, REQUEST_SYSFS);
552         mutex_unlock(&device_list_mutex);
553
554         if (p->pid)
555                 return sprintf(buf, "%s %d\n", p->requester, p->pid);
556         else
557                 return sprintf(buf, "%s\n", p->requester);
558 }
559
560 static ssize_t pwm_request_store(struct device *dev,
561                                  struct device_attribute *attr,
562                                  const char *buf,
563                                  size_t len)
564 {
565         struct pwm_channel *p = dev_get_drvdata(dev);
566         pwm_free(p);
567         return len;
568 }
569 static DEVICE_ATTR(request, 0644, pwm_request_show, pwm_request_store);
570
571 static const struct attribute *pwm_attrs[] =
572 {
573         &dev_attr_run.attr,
574         &dev_attr_polarity.attr,
575         &dev_attr_duty_ns.attr,
576         &dev_attr_period_ns.attr,
577         &dev_attr_request.attr,
578         NULL,
579 };
580
581 static const struct attribute_group pwm_device_attr_group = {
582         .attrs = (struct attribute **)pwm_attrs,
583 };
584
585 static int __pwm_create_sysfs(struct pwm_device *pwm)
586 {
587         int ret = 0;
588         struct device *dev;
589         int wchan;
590
591         for (wchan = 0; wchan < pwm->nchan; wchan++) {
592                 dev = device_create(&pwm_class, pwm->dev, MKDEV(0, 0),
593                                     pwm->channels + wchan,
594                                     "%s:%d", pwm->bus_id, wchan);
595                 if (!dev)
596                         goto err_dev_create;
597                 ret = sysfs_create_group(&dev->kobj, &pwm_device_attr_group);
598                 if (ret)
599                         goto err_dev_create;
600         }
601
602         return ret;
603
604 err_dev_create:
605         for (wchan = 0; wchan < pwm->nchan; wchan++) {
606                 dev = class_find_device(&pwm_class, NULL,
607                                         &pwm->channels[wchan],
608                                         __match_device);
609                 if (dev) {
610                         put_device(dev);
611                         device_unregister(dev);
612                 }
613         }
614
615         return ret;
616 }
617
618 static struct class_attribute pwm_class_attrs[] = {
619         __ATTR_NULL,
620 };
621
622 static struct class pwm_class = {
623         .name = "pwm",
624         .owner = THIS_MODULE,
625
626         .class_attrs = pwm_class_attrs,
627 };
628
629 static int __init pwm_init(void)
630 {
631         int ret;
632
633         /* TODO: how to deal with devices that register very early? */
634         pr_err("%s\n", __func__);
635         ret = class_register(&pwm_class);
636         if (ret < 0)
637                 return ret;
638
639         pwm_handler_workqueue = create_workqueue("pwmd");
640
641         return 0;
642 }
643 postcore_initcall(pwm_init);