Skip to content

Commit 7af26f3

Browse files
jbrun3tpH5
authored andcommitted
reset: amlogic: convert driver to regmap
To allow using the same driver for the main reset controller and the auxiliary ones embedded in the clock controllers, convert the the Amlogic reset driver to regmap. Reviewed-by: Neil Armstrong <[email protected]> Signed-off-by: Jerome Brunet <[email protected]> Reviewed-by: Philipp Zabel <[email protected]> Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Philipp Zabel <[email protected]>
1 parent 9852d85 commit 7af26f3

File tree

2 files changed

+44
-36
lines changed

2 files changed

+44
-36
lines changed

drivers/reset/Kconfig

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -157,6 +157,7 @@ config RESET_MESON
157157
tristate "Meson Reset Driver"
158158
depends on ARCH_MESON || COMPILE_TEST
159159
default ARCH_MESON
160+
select REGMAP_MMIO
160161
help
161162
This enables the reset driver for Amlogic Meson SoCs.
162163

drivers/reset/reset-meson.c

Lines changed: 43 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -11,62 +11,57 @@
1111
#include <linux/of.h>
1212
#include <linux/module.h>
1313
#include <linux/platform_device.h>
14+
#include <linux/regmap.h>
1415
#include <linux/reset-controller.h>
1516
#include <linux/slab.h>
1617
#include <linux/types.h>
1718

18-
#define BITS_PER_REG 32
19-
2019
struct meson_reset_param {
2120
int reg_count;
2221
int level_offset;
2322
};
2423

2524
struct meson_reset {
26-
void __iomem *reg_base;
2725
const struct meson_reset_param *param;
2826
struct reset_controller_dev rcdev;
29-
spinlock_t lock;
27+
struct regmap *map;
3028
};
3129

30+
static void meson_reset_offset_and_bit(struct meson_reset *data,
31+
unsigned long id,
32+
unsigned int *offset,
33+
unsigned int *bit)
34+
{
35+
unsigned int stride = regmap_get_reg_stride(data->map);
36+
37+
*offset = (id / (stride * BITS_PER_BYTE)) * stride;
38+
*bit = id % (stride * BITS_PER_BYTE);
39+
}
40+
3241
static int meson_reset_reset(struct reset_controller_dev *rcdev,
33-
unsigned long id)
42+
unsigned long id)
3443
{
3544
struct meson_reset *data =
3645
container_of(rcdev, struct meson_reset, rcdev);
37-
unsigned int bank = id / BITS_PER_REG;
38-
unsigned int offset = id % BITS_PER_REG;
39-
void __iomem *reg_addr = data->reg_base + (bank << 2);
46+
unsigned int offset, bit;
4047

41-
writel(BIT(offset), reg_addr);
48+
meson_reset_offset_and_bit(data, id, &offset, &bit);
4249

43-
return 0;
50+
return regmap_write(data->map, offset, BIT(bit));
4451
}
4552

4653
static int meson_reset_level(struct reset_controller_dev *rcdev,
4754
unsigned long id, bool assert)
4855
{
4956
struct meson_reset *data =
5057
container_of(rcdev, struct meson_reset, rcdev);
51-
unsigned int bank = id / BITS_PER_REG;
52-
unsigned int offset = id % BITS_PER_REG;
53-
void __iomem *reg_addr;
54-
unsigned long flags;
55-
u32 reg;
58+
unsigned int offset, bit;
5659

57-
reg_addr = data->reg_base + data->param->level_offset + (bank << 2);
60+
meson_reset_offset_and_bit(data, id, &offset, &bit);
61+
offset += data->param->level_offset;
5862

59-
spin_lock_irqsave(&data->lock, flags);
60-
61-
reg = readl(reg_addr);
62-
if (assert)
63-
writel(reg & ~BIT(offset), reg_addr);
64-
else
65-
writel(reg | BIT(offset), reg_addr);
66-
67-
spin_unlock_irqrestore(&data->lock, flags);
68-
69-
return 0;
63+
return regmap_update_bits(data->map, offset,
64+
BIT(bit), assert ? 0 : BIT(bit));
7065
}
7166

7267
static int meson_reset_assert(struct reset_controller_dev *rcdev,
@@ -119,30 +114,42 @@ static const struct of_device_id meson_reset_dt_ids[] = {
119114
};
120115
MODULE_DEVICE_TABLE(of, meson_reset_dt_ids);
121116

117+
static const struct regmap_config regmap_config = {
118+
.reg_bits = 32,
119+
.val_bits = 32,
120+
.reg_stride = 4,
121+
};
122+
122123
static int meson_reset_probe(struct platform_device *pdev)
123124
{
125+
struct device *dev = &pdev->dev;
124126
struct meson_reset *data;
127+
void __iomem *base;
125128

126-
data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
129+
data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL);
127130
if (!data)
128131
return -ENOMEM;
129132

130-
data->reg_base = devm_platform_ioremap_resource(pdev, 0);
131-
if (IS_ERR(data->reg_base))
132-
return PTR_ERR(data->reg_base);
133+
base = devm_platform_ioremap_resource(pdev, 0);
134+
if (IS_ERR(base))
135+
return PTR_ERR(base);
133136

134-
data->param = of_device_get_match_data(&pdev->dev);
137+
data->param = of_device_get_match_data(dev);
135138
if (!data->param)
136139
return -ENODEV;
137140

138-
spin_lock_init(&data->lock);
141+
data->map = devm_regmap_init_mmio(dev, base, &regmap_config);
142+
if (IS_ERR(data->map))
143+
return dev_err_probe(dev, PTR_ERR(data->map),
144+
"can't init regmap mmio region\n");
139145

140146
data->rcdev.owner = THIS_MODULE;
141-
data->rcdev.nr_resets = data->param->reg_count * BITS_PER_REG;
147+
data->rcdev.nr_resets = data->param->reg_count * BITS_PER_BYTE
148+
* regmap_config.reg_stride;
142149
data->rcdev.ops = &meson_reset_ops;
143-
data->rcdev.of_node = pdev->dev.of_node;
150+
data->rcdev.of_node = dev->of_node;
144151

145-
return devm_reset_controller_register(&pdev->dev, &data->rcdev);
152+
return devm_reset_controller_register(dev, &data->rcdev);
146153
}
147154

148155
static struct platform_driver meson_reset_driver = {

0 commit comments

Comments
 (0)