generic: mtd: backport SPI_NOR_HAS_LOCK
[openwrt/openwrt.git] / target / linux / layerscape / patches-4.4 / 7018-devres-add-devm_alloc_percpu.patch
1 From f7792176d939e79b4f525114a95d0fd8266bef8e Mon Sep 17 00:00:00 2001
2 From: Madalin Bucur <madalin.bucur@freescale.com>
3 Date: Wed, 19 Nov 2014 13:06:54 +0200
4 Subject: [PATCH 18/70] devres: add devm_alloc_percpu()
5
6 Introduce managed counterparts for alloc_percpu() and free_percpu().
7 Add devm_alloc_percpu() and devm_free_percpu() into the managed
8 interfaces list.
9
10 Signed-off-by: Madalin Bucur <madalin.bucur@freescale.com>
11
12 Change-Id: I93546348e7b0e1974fda8b6c7a3b3710ce45b724
13 Reviewed-on: http://git.am.freescale.net:8181/24140
14 Reviewed-by: Madalin-Cristian Bucur <madalin.bucur@freescale.com>
15 Tested-by: Madalin-Cristian Bucur <madalin.bucur@freescale.com>
16
17 Conflicts:
18 Documentation/driver-model/devres.txt
19 drivers/base/devres.c
20
21 Conflicts:
22 drivers/base/devres.c
23 ---
24 Documentation/driver-model/devres.txt | 4 +++
25 drivers/base/devres.c | 63 +++++++++++++++++++++++++++++++++
26 include/linux/device.h | 19 ++++++++++
27 3 files changed, 86 insertions(+)
28
29 --- a/Documentation/driver-model/devres.txt
30 +++ b/Documentation/driver-model/devres.txt
31 @@ -321,6 +321,10 @@ PHY
32 devm_usb_get_phy()
33 devm_usb_put_phy()
34
35 +PER-CPU MEM
36 + devm_alloc_percpu()
37 + devm_free_percpu()
38 +
39 PINCTRL
40 devm_pinctrl_get()
41 devm_pinctrl_put()
42 --- a/drivers/base/devres.c
43 +++ b/drivers/base/devres.c
44 @@ -985,3 +985,66 @@ void devm_free_pages(struct device *dev,
45 &devres));
46 }
47 EXPORT_SYMBOL_GPL(devm_free_pages);
48 +
49 +static void devm_percpu_release(struct device *dev, void *pdata)
50 +{
51 + void __percpu *p;
52 +
53 + p = *(void __percpu **)pdata;
54 + free_percpu(p);
55 +}
56 +
57 +static int devm_percpu_match(struct device *dev, void *data, void *p)
58 +{
59 + struct devres *devr = container_of(data, struct devres, data);
60 +
61 + return *(void **)devr->data == p;
62 +}
63 +
64 +/**
65 + * __devm_alloc_percpu - Resource-managed alloc_percpu
66 + * @dev: Device to allocate per-cpu memory for
67 + * @size: Size of per-cpu memory to allocate
68 + * @align: Alignement of per-cpu memory to allocate
69 + *
70 + * Managed alloc_percpu. Per-cpu memory allocated with this function is
71 + * automatically freed on driver detach.
72 + *
73 + * RETURNS:
74 + * Pointer to allocated memory on success, NULL on failure.
75 + */
76 +void __percpu *__devm_alloc_percpu(struct device *dev, size_t size,
77 + size_t align)
78 +{
79 + void *p;
80 + void __percpu *pcpu;
81 +
82 + pcpu = __alloc_percpu(size, align);
83 + if (!pcpu)
84 + return NULL;
85 +
86 + p = devres_alloc(devm_percpu_release, sizeof(void *), GFP_KERNEL);
87 + if (!p)
88 + return NULL;
89 +
90 + *(void __percpu **)p = pcpu;
91 +
92 + devres_add(dev, p);
93 +
94 + return pcpu;
95 +}
96 +EXPORT_SYMBOL_GPL(__devm_alloc_percpu);
97 +
98 +/**
99 + * devm_free_percpu - Resource-managed free_percpu
100 + * @dev: Device this memory belongs to
101 + * @pdata: Per-cpu memory to free
102 + *
103 + * Free memory allocated with devm_alloc_percpu().
104 + */
105 +void devm_free_percpu(struct device *dev, void __percpu *pdata)
106 +{
107 + WARN_ON(devres_destroy(dev, devm_percpu_release, devm_percpu_match,
108 + (void *)pdata));
109 +}
110 +EXPORT_SYMBOL_GPL(devm_free_percpu);
111 --- a/include/linux/device.h
112 +++ b/include/linux/device.h
113 @@ -681,6 +681,25 @@ void __iomem *devm_ioremap_resource(stru
114 int devm_add_action(struct device *dev, void (*action)(void *), void *data);
115 void devm_remove_action(struct device *dev, void (*action)(void *), void *data);
116
117 +/**
118 + * devm_alloc_percpu - Resource-managed alloc_percpu
119 + * @dev: Device to allocate per-cpu memory for
120 + * @type: Type to allocate per-cpu memory for
121 + *
122 + * Managed alloc_percpu. Per-cpu memory allocated with this function is
123 + * automatically freed on driver detach.
124 + *
125 + * RETURNS:
126 + * Pointer to allocated memory on success, NULL on failure.
127 + */
128 +#define devm_alloc_percpu(dev, type) \
129 + (typeof(type) __percpu *)__devm_alloc_percpu(dev, sizeof(type), \
130 + __alignof__(type))
131 +
132 +void __percpu *__devm_alloc_percpu(struct device *dev, size_t size,
133 + size_t align);
134 +void devm_free_percpu(struct device *dev, void __percpu *pdata);
135 +
136 struct device_dma_parameters {
137 /*
138 * a low level driver may set these to teach IOMMU code about