]> rtime.felk.cvut.cz Git - linux-imx.git/blob - drivers/pinctrl/pinconf.c
Merge tag 'fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/arm...
[linux-imx.git] / drivers / pinctrl / pinconf.c
1 /*
2  * Core driver for the pin config portions of the pin control subsystem
3  *
4  * Copyright (C) 2011 ST-Ericsson SA
5  * Written on behalf of Linaro for ST-Ericsson
6  *
7  * Author: Linus Walleij <linus.walleij@linaro.org>
8  *
9  * License terms: GNU General Public License (GPL) version 2
10  */
11 #define pr_fmt(fmt) "pinconfig core: " fmt
12
13 #include <linux/kernel.h>
14 #include <linux/module.h>
15 #include <linux/init.h>
16 #include <linux/device.h>
17 #include <linux/slab.h>
18 #include <linux/debugfs.h>
19 #include <linux/seq_file.h>
20 #include <linux/uaccess.h>
21 #include <linux/pinctrl/machine.h>
22 #include <linux/pinctrl/pinctrl.h>
23 #include <linux/pinctrl/pinconf.h>
24 #include "core.h"
25 #include "pinconf.h"
26
27 int pinconf_check_ops(struct pinctrl_dev *pctldev)
28 {
29         const struct pinconf_ops *ops = pctldev->desc->confops;
30
31         /* We must be able to read out pin status */
32         if (!ops->pin_config_get && !ops->pin_config_group_get) {
33                 dev_err(pctldev->dev,
34                         "pinconf must be able to read out pin status\n");
35                 return -EINVAL;
36         }
37         /* We have to be able to config the pins in SOME way */
38         if (!ops->pin_config_set && !ops->pin_config_group_set) {
39                 dev_err(pctldev->dev,
40                         "pinconf has to be able to set a pins config\n");
41                 return -EINVAL;
42         }
43         return 0;
44 }
45
46 int pinconf_validate_map(struct pinctrl_map const *map, int i)
47 {
48         if (!map->data.configs.group_or_pin) {
49                 pr_err("failed to register map %s (%d): no group/pin given\n",
50                        map->name, i);
51                 return -EINVAL;
52         }
53
54         if (!map->data.configs.num_configs ||
55                         !map->data.configs.configs) {
56                 pr_err("failed to register map %s (%d): no configs given\n",
57                        map->name, i);
58                 return -EINVAL;
59         }
60
61         return 0;
62 }
63
64 int pin_config_get_for_pin(struct pinctrl_dev *pctldev, unsigned pin,
65                            unsigned long *config)
66 {
67         const struct pinconf_ops *ops = pctldev->desc->confops;
68
69         if (!ops || !ops->pin_config_get) {
70                 dev_err(pctldev->dev, "cannot get pin configuration, missing "
71                         "pin_config_get() function in driver\n");
72                 return -EINVAL;
73         }
74
75         return ops->pin_config_get(pctldev, pin, config);
76 }
77
78 int pin_config_group_get(const char *dev_name, const char *pin_group,
79                          unsigned long *config)
80 {
81         struct pinctrl_dev *pctldev;
82         const struct pinconf_ops *ops;
83         int selector, ret;
84
85         pctldev = get_pinctrl_dev_from_devname(dev_name);
86         if (!pctldev) {
87                 ret = -EINVAL;
88                 return ret;
89         }
90
91         mutex_lock(&pctldev->mutex);
92
93         ops = pctldev->desc->confops;
94
95         if (!ops || !ops->pin_config_group_get) {
96                 dev_err(pctldev->dev, "cannot get configuration for pin "
97                         "group, missing group config get function in "
98                         "driver\n");
99                 ret = -EINVAL;
100                 goto unlock;
101         }
102
103         selector = pinctrl_get_group_selector(pctldev, pin_group);
104         if (selector < 0) {
105                 ret = selector;
106                 goto unlock;
107         }
108
109         ret = ops->pin_config_group_get(pctldev, selector, config);
110
111 unlock:
112         mutex_unlock(&pctldev->mutex);
113         return ret;
114 }
115
116 int pinconf_map_to_setting(struct pinctrl_map const *map,
117                           struct pinctrl_setting *setting)
118 {
119         struct pinctrl_dev *pctldev = setting->pctldev;
120         int pin;
121
122         switch (setting->type) {
123         case PIN_MAP_TYPE_CONFIGS_PIN:
124                 pin = pin_get_from_name(pctldev,
125                                         map->data.configs.group_or_pin);
126                 if (pin < 0) {
127                         dev_err(pctldev->dev, "could not map pin config for \"%s\"",
128                                 map->data.configs.group_or_pin);
129                         return pin;
130                 }
131                 setting->data.configs.group_or_pin = pin;
132                 break;
133         case PIN_MAP_TYPE_CONFIGS_GROUP:
134                 pin = pinctrl_get_group_selector(pctldev,
135                                          map->data.configs.group_or_pin);
136                 if (pin < 0) {
137                         dev_err(pctldev->dev, "could not map group config for \"%s\"",
138                                 map->data.configs.group_or_pin);
139                         return pin;
140                 }
141                 setting->data.configs.group_or_pin = pin;
142                 break;
143         default:
144                 return -EINVAL;
145         }
146
147         setting->data.configs.num_configs = map->data.configs.num_configs;
148         setting->data.configs.configs = map->data.configs.configs;
149
150         return 0;
151 }
152
153 void pinconf_free_setting(struct pinctrl_setting const *setting)
154 {
155 }
156
157 int pinconf_apply_setting(struct pinctrl_setting const *setting)
158 {
159         struct pinctrl_dev *pctldev = setting->pctldev;
160         const struct pinconf_ops *ops = pctldev->desc->confops;
161         int i, ret;
162
163         if (!ops) {
164                 dev_err(pctldev->dev, "missing confops\n");
165                 return -EINVAL;
166         }
167
168         switch (setting->type) {
169         case PIN_MAP_TYPE_CONFIGS_PIN:
170                 if (!ops->pin_config_set) {
171                         dev_err(pctldev->dev, "missing pin_config_set op\n");
172                         return -EINVAL;
173                 }
174                 for (i = 0; i < setting->data.configs.num_configs; i++) {
175                         ret = ops->pin_config_set(pctldev,
176                                         setting->data.configs.group_or_pin,
177                                         setting->data.configs.configs[i]);
178                         if (ret < 0) {
179                                 dev_err(pctldev->dev,
180                                         "pin_config_set op failed for pin %d config %08lx\n",
181                                         setting->data.configs.group_or_pin,
182                                         setting->data.configs.configs[i]);
183                                 return ret;
184                         }
185                 }
186                 break;
187         case PIN_MAP_TYPE_CONFIGS_GROUP:
188                 if (!ops->pin_config_group_set) {
189                         dev_err(pctldev->dev,
190                                 "missing pin_config_group_set op\n");
191                         return -EINVAL;
192                 }
193                 for (i = 0; i < setting->data.configs.num_configs; i++) {
194                         ret = ops->pin_config_group_set(pctldev,
195                                         setting->data.configs.group_or_pin,
196                                         setting->data.configs.configs[i]);
197                         if (ret < 0) {
198                                 dev_err(pctldev->dev,
199                                         "pin_config_group_set op failed for group %d config %08lx\n",
200                                         setting->data.configs.group_or_pin,
201                                         setting->data.configs.configs[i]);
202                                 return ret;
203                         }
204                 }
205                 break;
206         default:
207                 return -EINVAL;
208         }
209
210         return 0;
211 }
212
213 #ifdef CONFIG_DEBUG_FS
214
215 void pinconf_show_map(struct seq_file *s, struct pinctrl_map const *map)
216 {
217         struct pinctrl_dev *pctldev;
218         const struct pinconf_ops *confops;
219         int i;
220
221         pctldev = get_pinctrl_dev_from_devname(map->ctrl_dev_name);
222         if (pctldev)
223                 confops = pctldev->desc->confops;
224         else
225                 confops = NULL;
226
227         switch (map->type) {
228         case PIN_MAP_TYPE_CONFIGS_PIN:
229                 seq_printf(s, "pin ");
230                 break;
231         case PIN_MAP_TYPE_CONFIGS_GROUP:
232                 seq_printf(s, "group ");
233                 break;
234         default:
235                 break;
236         }
237
238         seq_printf(s, "%s\n", map->data.configs.group_or_pin);
239
240         for (i = 0; i < map->data.configs.num_configs; i++) {
241                 seq_printf(s, "config ");
242                 if (confops && confops->pin_config_config_dbg_show)
243                         confops->pin_config_config_dbg_show(pctldev, s,
244                                                 map->data.configs.configs[i]);
245                 else
246                         seq_printf(s, "%08lx", map->data.configs.configs[i]);
247                 seq_printf(s, "\n");
248         }
249 }
250
251 void pinconf_show_setting(struct seq_file *s,
252                           struct pinctrl_setting const *setting)
253 {
254         struct pinctrl_dev *pctldev = setting->pctldev;
255         const struct pinctrl_ops *pctlops = pctldev->desc->pctlops;
256         const struct pinconf_ops *confops = pctldev->desc->confops;
257         struct pin_desc *desc;
258         int i;
259
260         switch (setting->type) {
261         case PIN_MAP_TYPE_CONFIGS_PIN:
262                 desc = pin_desc_get(setting->pctldev,
263                                     setting->data.configs.group_or_pin);
264                 seq_printf(s, "pin %s (%d)",
265                            desc->name ? desc->name : "unnamed",
266                            setting->data.configs.group_or_pin);
267                 break;
268         case PIN_MAP_TYPE_CONFIGS_GROUP:
269                 seq_printf(s, "group %s (%d)",
270                            pctlops->get_group_name(pctldev,
271                                         setting->data.configs.group_or_pin),
272                            setting->data.configs.group_or_pin);
273                 break;
274         default:
275                 break;
276         }
277
278         /*
279          * FIXME: We should really get the pin controler to dump the config
280          * values, so they can be decoded to something meaningful.
281          */
282         for (i = 0; i < setting->data.configs.num_configs; i++) {
283                 seq_printf(s, " ");
284                 if (confops && confops->pin_config_config_dbg_show)
285                         confops->pin_config_config_dbg_show(pctldev, s,
286                                 setting->data.configs.configs[i]);
287                 else
288                         seq_printf(s, "%08lx",
289                                    setting->data.configs.configs[i]);
290         }
291
292         seq_printf(s, "\n");
293 }
294
295 static void pinconf_dump_pin(struct pinctrl_dev *pctldev,
296                              struct seq_file *s, int pin)
297 {
298         const struct pinconf_ops *ops = pctldev->desc->confops;
299
300         /* no-op when not using generic pin config */
301         pinconf_generic_dump_pin(pctldev, s, pin);
302         if (ops && ops->pin_config_dbg_show)
303                 ops->pin_config_dbg_show(pctldev, s, pin);
304 }
305
306 static int pinconf_pins_show(struct seq_file *s, void *what)
307 {
308         struct pinctrl_dev *pctldev = s->private;
309         const struct pinconf_ops *ops = pctldev->desc->confops;
310         unsigned i, pin;
311
312         if (!ops || !ops->pin_config_get)
313                 return 0;
314
315         seq_puts(s, "Pin config settings per pin\n");
316         seq_puts(s, "Format: pin (name): configs\n");
317
318         mutex_lock(&pctldev->mutex);
319
320         /* The pin number can be retrived from the pin controller descriptor */
321         for (i = 0; i < pctldev->desc->npins; i++) {
322                 struct pin_desc *desc;
323
324                 pin = pctldev->desc->pins[i].number;
325                 desc = pin_desc_get(pctldev, pin);
326                 /* Skip if we cannot search the pin */
327                 if (desc == NULL)
328                         continue;
329
330                 seq_printf(s, "pin %d (%s):", pin,
331                            desc->name ? desc->name : "unnamed");
332
333                 pinconf_dump_pin(pctldev, s, pin);
334
335                 seq_printf(s, "\n");
336         }
337
338         mutex_unlock(&pctldev->mutex);
339
340         return 0;
341 }
342
343 static void pinconf_dump_group(struct pinctrl_dev *pctldev,
344                                struct seq_file *s, unsigned selector,
345                                const char *gname)
346 {
347         const struct pinconf_ops *ops = pctldev->desc->confops;
348
349         /* no-op when not using generic pin config */
350         pinconf_generic_dump_group(pctldev, s, gname);
351         if (ops && ops->pin_config_group_dbg_show)
352                 ops->pin_config_group_dbg_show(pctldev, s, selector);
353 }
354
355 static int pinconf_groups_show(struct seq_file *s, void *what)
356 {
357         struct pinctrl_dev *pctldev = s->private;
358         const struct pinctrl_ops *pctlops = pctldev->desc->pctlops;
359         const struct pinconf_ops *ops = pctldev->desc->confops;
360         unsigned ngroups = pctlops->get_groups_count(pctldev);
361         unsigned selector = 0;
362
363         if (!ops || !ops->pin_config_group_get)
364                 return 0;
365
366         seq_puts(s, "Pin config settings per pin group\n");
367         seq_puts(s, "Format: group (name): configs\n");
368
369         while (selector < ngroups) {
370                 const char *gname = pctlops->get_group_name(pctldev, selector);
371
372                 seq_printf(s, "%u (%s):", selector, gname);
373                 pinconf_dump_group(pctldev, s, selector, gname);
374                 seq_printf(s, "\n");
375
376                 selector++;
377         }
378
379         return 0;
380 }
381
382 static int pinconf_pins_open(struct inode *inode, struct file *file)
383 {
384         return single_open(file, pinconf_pins_show, inode->i_private);
385 }
386
387 static int pinconf_groups_open(struct inode *inode, struct file *file)
388 {
389         return single_open(file, pinconf_groups_show, inode->i_private);
390 }
391
392 static const struct file_operations pinconf_pins_ops = {
393         .open           = pinconf_pins_open,
394         .read           = seq_read,
395         .llseek         = seq_lseek,
396         .release        = single_release,
397 };
398
399 static const struct file_operations pinconf_groups_ops = {
400         .open           = pinconf_groups_open,
401         .read           = seq_read,
402         .llseek         = seq_lseek,
403         .release        = single_release,
404 };
405
406 #define MAX_NAME_LEN 15
407
408 struct dbg_cfg {
409         enum pinctrl_map_type map_type;
410         char dev_name[MAX_NAME_LEN+1];
411         char state_name[MAX_NAME_LEN+1];
412         char pin_name[MAX_NAME_LEN+1];
413 };
414
415 /*
416  * Goal is to keep this structure as global in order to simply read the
417  * pinconf-config file after a write to check config is as expected
418  */
419 static struct dbg_cfg pinconf_dbg_conf;
420
421 /**
422  * pinconf_dbg_config_print() - display the pinctrl config from the pinctrl
423  * map, of the dev/pin/state that was last written to pinconf-config file.
424  * @s: string filled in  with config description
425  * @d: not used
426  */
427 static int pinconf_dbg_config_print(struct seq_file *s, void *d)
428 {
429         struct pinctrl_maps *maps_node;
430         const struct pinctrl_map *map;
431         struct pinctrl_dev *pctldev = NULL;
432         const struct pinconf_ops *confops = NULL;
433         const struct pinctrl_map_configs *configs;
434         struct dbg_cfg *dbg = &pinconf_dbg_conf;
435         int i, j;
436         bool found = false;
437         unsigned long config;
438
439         mutex_lock(&pinctrl_maps_mutex);
440
441         /* Parse the pinctrl map and look for the elected pin/state */
442         for_each_maps(maps_node, i, map) {
443                 if (map->type != dbg->map_type)
444                         continue;
445                 if (strcmp(map->dev_name, dbg->dev_name))
446                         continue;
447                 if (strcmp(map->name, dbg->state_name))
448                         continue;
449
450                 for (j = 0; j < map->data.configs.num_configs; j++) {
451                         if (!strcmp(map->data.configs.group_or_pin,
452                                         dbg->pin_name)) {
453                                 /*
454                                  * We found the right pin / state, read the
455                                  * config and he pctldev for later use
456                                  */
457                                 configs = &map->data.configs;
458                                 pctldev = get_pinctrl_dev_from_devname
459                                         (map->ctrl_dev_name);
460                                 found = true;
461                                 break;
462                         }
463                 }
464         }
465
466         if (!found) {
467                 seq_printf(s, "No config found for dev/state/pin, expected:\n");
468                 seq_printf(s, "Searched dev:%s\n", dbg->dev_name);
469                 seq_printf(s, "Searched state:%s\n", dbg->state_name);
470                 seq_printf(s, "Searched pin:%s\n", dbg->pin_name);
471                 seq_printf(s, "Use: modify config_pin <devname> "\
472                                 "<state> <pinname> <value>\n");
473                 goto exit;
474         }
475
476         config = *(configs->configs);
477         seq_printf(s, "Dev %s has config of %s in state %s: 0x%08lX\n",
478                         dbg->dev_name, dbg->pin_name,
479                         dbg->state_name, config);
480
481         if (pctldev)
482                 confops = pctldev->desc->confops;
483
484         if (confops && confops->pin_config_config_dbg_show)
485                 confops->pin_config_config_dbg_show(pctldev, s, config);
486
487 exit:
488         mutex_unlock(&pinctrl_maps_mutex);
489
490         return 0;
491 }
492
493 /**
494  * pinconf_dbg_config_write() - modify the pinctrl config in the pinctrl
495  * map, of a dev/pin/state entry based on user entries to pinconf-config
496  * @user_buf: contains the modification request with expected format:
497  *     modify config_pin <devicename> <state> <pinname> <newvalue>
498  * modify is literal string, alternatives like add/delete not supported yet
499  * config_pin is literal, alternatives like config_mux not supported yet
500  * <devicename> <state> <pinname> are values that should match the pinctrl-maps
501  * <newvalue> reflects the new config and is driver dependant
502  */
503 static int pinconf_dbg_config_write(struct file *file,
504         const char __user *user_buf, size_t count, loff_t *ppos)
505 {
506         struct pinctrl_maps *maps_node;
507         const struct pinctrl_map *map;
508         struct pinctrl_dev *pctldev = NULL;
509         const struct pinconf_ops *confops = NULL;
510         struct dbg_cfg *dbg = &pinconf_dbg_conf;
511         const struct pinctrl_map_configs *configs;
512         char config[MAX_NAME_LEN+1];
513         bool found = false;
514         char buf[128];
515         char *b = &buf[0];
516         int buf_size;
517         char *token;
518         int i;
519
520         /* Get userspace string and assure termination */
521         buf_size = min(count, (sizeof(buf)-1));
522         if (copy_from_user(buf, user_buf, buf_size))
523                 return -EFAULT;
524         buf[buf_size] = 0;
525
526         /*
527          * need to parse entry and extract parameters:
528          * modify configs_pin devicename state pinname newvalue
529          */
530
531         /* Get arg: 'modify' */
532         token = strsep(&b, " ");
533         if (!token)
534                 return -EINVAL;
535         if (strcmp(token, "modify"))
536                 return -EINVAL;
537
538         /* Get arg type: "config_pin" type supported so far */
539         token = strsep(&b, " ");
540         if (!token)
541                 return -EINVAL;
542         if (strcmp(token, "config_pin"))
543                 return -EINVAL;
544         dbg->map_type = PIN_MAP_TYPE_CONFIGS_PIN;
545
546         /* get arg 'device_name' */
547         token = strsep(&b, " ");
548         if (token == NULL)
549                 return -EINVAL;
550         if (strlen(token) >= MAX_NAME_LEN)
551                 return -EINVAL;
552         strncpy(dbg->dev_name, token, MAX_NAME_LEN);
553
554         /* get arg 'state_name' */
555         token = strsep(&b, " ");
556         if (token == NULL)
557                 return -EINVAL;
558         if (strlen(token) >= MAX_NAME_LEN)
559                 return -EINVAL;
560         strncpy(dbg->state_name, token, MAX_NAME_LEN);
561
562         /* get arg 'pin_name' */
563         token = strsep(&b, " ");
564         if (token == NULL)
565                 return -EINVAL;
566         if (strlen(token) >= MAX_NAME_LEN)
567                 return -EINVAL;
568         strncpy(dbg->pin_name, token, MAX_NAME_LEN);
569
570         /* get new_value of config' */
571         token = strsep(&b, " ");
572         if (token == NULL)
573                 return -EINVAL;
574         if (strlen(token) >= MAX_NAME_LEN)
575                 return -EINVAL;
576         strncpy(config, token, MAX_NAME_LEN);
577
578         mutex_lock(&pinctrl_maps_mutex);
579
580         /* Parse the pinctrl map and look for the selected dev/state/pin */
581         for_each_maps(maps_node, i, map) {
582                 if (strcmp(map->dev_name, dbg->dev_name))
583                         continue;
584                 if (map->type != dbg->map_type)
585                         continue;
586                 if (strcmp(map->name, dbg->state_name))
587                         continue;
588
589                 /*  we found the right pin / state, so overwrite config */
590                 if (!strcmp(map->data.configs.group_or_pin, dbg->pin_name)) {
591                         found = true;
592                         pctldev = get_pinctrl_dev_from_devname(
593                                         map->ctrl_dev_name);
594                         configs = &map->data.configs;
595                         break;
596                 }
597         }
598
599         if (!found) {
600                 count = -EINVAL;
601                 goto exit;
602         }
603
604         if (pctldev)
605                 confops = pctldev->desc->confops;
606
607         if (confops && confops->pin_config_dbg_parse_modify) {
608                 for (i = 0; i < configs->num_configs; i++) {
609                         confops->pin_config_dbg_parse_modify(pctldev,
610                                                      config,
611                                                      &configs->configs[i]);
612                 }
613         }
614
615 exit:
616         mutex_unlock(&pinctrl_maps_mutex);
617
618         return count;
619 }
620
621 static int pinconf_dbg_config_open(struct inode *inode, struct file *file)
622 {
623         return single_open(file, pinconf_dbg_config_print, inode->i_private);
624 }
625
626 static const struct file_operations pinconf_dbg_pinconfig_fops = {
627         .open = pinconf_dbg_config_open,
628         .write = pinconf_dbg_config_write,
629         .read = seq_read,
630         .llseek = seq_lseek,
631         .release = single_release,
632         .owner = THIS_MODULE,
633 };
634
635 void pinconf_init_device_debugfs(struct dentry *devroot,
636                          struct pinctrl_dev *pctldev)
637 {
638         debugfs_create_file("pinconf-pins", S_IFREG | S_IRUGO,
639                             devroot, pctldev, &pinconf_pins_ops);
640         debugfs_create_file("pinconf-groups", S_IFREG | S_IRUGO,
641                             devroot, pctldev, &pinconf_groups_ops);
642         debugfs_create_file("pinconf-config",  (S_IRUGO | S_IWUSR | S_IWGRP),
643                             devroot, pctldev, &pinconf_dbg_pinconfig_fops);
644 }
645
646 #endif