mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-08-21 08:19:28 +00:00
![Robert Marko](/assets/img/avatar_default.png)
This patch adds the support for giving the complete bitmask in reset structure and reset operation will use this bitmask for all reset operations. Currently, reset structure only takes a single bit for each reset and then calculates the bitmask by using the BIT() macro. However, this is not sufficient anymore for newer SoC-s like IPQ8074, IPQ6018 and more, since their networking resets require multiple bits to be asserted in order to properly reset the HW block completely. So, in order to allow asserting multiple bits add "bitmask" field to qcom_reset_map, and then use that bitmask value if its populated in the driver, if its not populated, then we just default to existing behaviour and calculate the bitmask on the fly. Signed-off-by: Robert Marko <robimarko@gmail.com> Signed-off-by: Bjorn Andersson <andersson@kernel.org> Link: https://lore.kernel.org/r/20221107132901.489240-1-robimarko@gmail.com
57 lines
1.4 KiB
C
57 lines
1.4 KiB
C
// SPDX-License-Identifier: GPL-2.0-only
|
|
/*
|
|
* Copyright (c) 2013, The Linux Foundation. All rights reserved.
|
|
*/
|
|
|
|
#include <linux/bitops.h>
|
|
#include <linux/export.h>
|
|
#include <linux/regmap.h>
|
|
#include <linux/reset-controller.h>
|
|
#include <linux/delay.h>
|
|
|
|
#include "reset.h"
|
|
|
|
static int qcom_reset(struct reset_controller_dev *rcdev, unsigned long id)
|
|
{
|
|
struct qcom_reset_controller *rst = to_qcom_reset_controller(rcdev);
|
|
|
|
rcdev->ops->assert(rcdev, id);
|
|
udelay(rst->reset_map[id].udelay ?: 1); /* use 1 us as default */
|
|
rcdev->ops->deassert(rcdev, id);
|
|
return 0;
|
|
}
|
|
|
|
static int
|
|
qcom_reset_assert(struct reset_controller_dev *rcdev, unsigned long id)
|
|
{
|
|
struct qcom_reset_controller *rst;
|
|
const struct qcom_reset_map *map;
|
|
u32 mask;
|
|
|
|
rst = to_qcom_reset_controller(rcdev);
|
|
map = &rst->reset_map[id];
|
|
mask = map->bitmask ? map->bitmask : BIT(map->bit);
|
|
|
|
return regmap_update_bits(rst->regmap, map->reg, mask, mask);
|
|
}
|
|
|
|
static int
|
|
qcom_reset_deassert(struct reset_controller_dev *rcdev, unsigned long id)
|
|
{
|
|
struct qcom_reset_controller *rst;
|
|
const struct qcom_reset_map *map;
|
|
u32 mask;
|
|
|
|
rst = to_qcom_reset_controller(rcdev);
|
|
map = &rst->reset_map[id];
|
|
mask = map->bitmask ? map->bitmask : BIT(map->bit);
|
|
|
|
return regmap_update_bits(rst->regmap, map->reg, mask, 0);
|
|
}
|
|
|
|
const struct reset_control_ops qcom_reset_ops = {
|
|
.reset = qcom_reset,
|
|
.assert = qcom_reset_assert,
|
|
.deassert = qcom_reset_deassert,
|
|
};
|
|
EXPORT_SYMBOL_GPL(qcom_reset_ops);
|