Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 302328
b: refs/heads/master
c: 57291ce
h: refs/heads/master
v: v3
  • Loading branch information
Stephen Warren authored and Linus Walleij committed Apr 18, 2012
1 parent 5c7f4e2 commit 716b68d
Show file tree
Hide file tree
Showing 7 changed files with 358 additions and 19 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: d26bc49fa401be2b71838b6a4b387196cd12a534
refs/heads/master: 57291ce295c0aca738dd284c4a9c591c09ebee71
1 change: 1 addition & 0 deletions trunk/drivers/pinctrl/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ ccflags-$(CONFIG_DEBUG_PINCTRL) += -DDEBUG
obj-$(CONFIG_PINCTRL) += core.o
obj-$(CONFIG_PINMUX) += pinmux.o
obj-$(CONFIG_PINCONF) += pinconf.o
obj-$(CONFIG_OF) += devicetree.o
obj-$(CONFIG_GENERIC_PINCONF) += pinconf-generic.o
obj-$(CONFIG_PINCTRL_PXA3xx) += pinctrl-pxa3xx.o
obj-$(CONFIG_PINCTRL_MMP2) += pinctrl-mmp2.o
Expand Down
72 changes: 55 additions & 17 deletions trunk/drivers/pinctrl/core.c
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
#include <linux/pinctrl/pinctrl.h>
#include <linux/pinctrl/machine.h>
#include "core.h"
#include "devicetree.h"
#include "pinmux.h"
#include "pinconf.h"

Expand All @@ -45,7 +46,7 @@ struct pinctrl_maps {
DEFINE_MUTEX(pinctrl_mutex);

/* Global list of pin control devices (struct pinctrl_dev) */
static LIST_HEAD(pinctrldev_list);
LIST_HEAD(pinctrldev_list);

/* List of pin controller handles (struct pinctrl) */
static LIST_HEAD(pinctrl_list);
Expand Down Expand Up @@ -579,6 +580,13 @@ static struct pinctrl *create_pinctrl(struct device *dev)
}
p->dev = dev;
INIT_LIST_HEAD(&p->states);
INIT_LIST_HEAD(&p->dt_maps);

ret = pinctrl_dt_to_map(p);
if (ret < 0) {
kfree(p);
return ERR_PTR(ret);
}

devname = dev_name(dev);

Expand Down Expand Up @@ -662,6 +670,8 @@ static void pinctrl_put_locked(struct pinctrl *p, bool inlist)
kfree(state);
}

pinctrl_dt_free_maps(p);

if (inlist)
list_del(&p->node);
kfree(p);
Expand Down Expand Up @@ -787,15 +797,8 @@ int pinctrl_select_state(struct pinctrl *p, struct pinctrl_state *state)
}
EXPORT_SYMBOL_GPL(pinctrl_select_state);

/**
* pinctrl_register_mappings() - register a set of pin controller mappings
* @maps: the pincontrol mappings table to register. This should probably be
* marked with __initdata so it can be discarded after boot. This
* function will perform a shallow copy for the mapping entries.
* @num_maps: the number of maps in the mapping table
*/
int pinctrl_register_mappings(struct pinctrl_map const *maps,
unsigned num_maps)
int pinctrl_register_map(struct pinctrl_map const *maps, unsigned num_maps,
bool dup, bool locked)
{
int i, ret;
struct pinctrl_maps *maps_node;
Expand Down Expand Up @@ -851,20 +854,52 @@ int pinctrl_register_mappings(struct pinctrl_map const *maps,
}

maps_node->num_maps = num_maps;
maps_node->maps = kmemdup(maps, sizeof(*maps) * num_maps, GFP_KERNEL);
if (!maps_node->maps) {
pr_err("failed to duplicate mapping table\n");
kfree(maps_node);
return -ENOMEM;
if (dup) {
maps_node->maps = kmemdup(maps, sizeof(*maps) * num_maps,
GFP_KERNEL);
if (!maps_node->maps) {
pr_err("failed to duplicate mapping table\n");
kfree(maps_node);
return -ENOMEM;
}
} else {
maps_node->maps = maps;
}

mutex_lock(&pinctrl_mutex);
if (!locked)
mutex_lock(&pinctrl_mutex);
list_add_tail(&maps_node->node, &pinctrl_maps);
mutex_unlock(&pinctrl_mutex);
if (!locked)
mutex_unlock(&pinctrl_mutex);

return 0;
}

/**
* pinctrl_register_mappings() - register a set of pin controller mappings
* @maps: the pincontrol mappings table to register. This should probably be
* marked with __initdata so it can be discarded after boot. This
* function will perform a shallow copy for the mapping entries.
* @num_maps: the number of maps in the mapping table
*/
int pinctrl_register_mappings(struct pinctrl_map const *maps,
unsigned num_maps)
{
return pinctrl_register_map(maps, num_maps, true, false);
}

void pinctrl_unregister_map(struct pinctrl_map const *map)
{
struct pinctrl_maps *maps_node;

list_for_each_entry(maps_node, &pinctrl_maps, node) {
if (maps_node->maps == map) {
list_del(&maps_node->node);
return;
}
}
}

#ifdef CONFIG_DEBUG_FS

static int pinctrl_pins_show(struct seq_file *s, void *what)
Expand Down Expand Up @@ -1231,6 +1266,9 @@ static int pinctrl_check_ops(struct pinctrl_dev *pctldev)
!ops->get_group_pins)
return -EINVAL;

if (ops->dt_node_to_map && !ops->dt_free_map)
return -EINVAL;

return 0;
}

Expand Down
11 changes: 10 additions & 1 deletion trunk/drivers/pinctrl/core.h
Original file line number Diff line number Diff line change
Expand Up @@ -52,12 +52,15 @@ struct pinctrl_dev {
* @dev: the device using this pin control handle
* @states: a list of states for this device
* @state: the current state
* @dt_maps: the mapping table chunks dynamically parsed from device tree for
* this device, if any
*/
struct pinctrl {
struct list_head node;
struct device *dev;
struct list_head states;
struct pinctrl_state *state;
struct list_head dt_maps;
};

/**
Expand Down Expand Up @@ -100,7 +103,8 @@ struct pinctrl_setting_configs {
* struct pinctrl_setting - an individual mux or config setting
* @node: list node for struct pinctrl_settings's @settings field
* @type: the type of setting
* @pctldev: pin control device handling to be programmed
* @pctldev: pin control device handling to be programmed. Not used for
* PIN_MAP_TYPE_DUMMY_STATE.
* @data: Data specific to the setting type
*/
struct pinctrl_setting {
Expand Down Expand Up @@ -153,4 +157,9 @@ static inline struct pin_desc *pin_desc_get(struct pinctrl_dev *pctldev,
return radix_tree_lookup(&pctldev->pin_desc_tree, pin);
}

int pinctrl_register_map(struct pinctrl_map const *maps, unsigned num_maps,
bool dup, bool locked);
void pinctrl_unregister_map(struct pinctrl_map const *map);

extern struct mutex pinctrl_mutex;
extern struct list_head pinctrldev_list;
Loading

0 comments on commit 716b68d

Please sign in to comment.