1d2912cb1SThomas Gleixner // SPDX-License-Identifier: GPL-2.0-only 2dc606c52SThierry Reding /* 3dc606c52SThierry Reding * Copyright (C) 2016 NVIDIA Corporation 4dc606c52SThierry Reding */ 5dc606c52SThierry Reding 6dc606c52SThierry Reding #include <linux/reset-controller.h> 7dc606c52SThierry Reding 8dc606c52SThierry Reding #include <soc/tegra/bpmp.h> 9dc606c52SThierry Reding #include <soc/tegra/bpmp-abi.h> 10dc606c52SThierry Reding 11dc606c52SThierry Reding static struct tegra_bpmp *to_tegra_bpmp(struct reset_controller_dev *rstc) 12dc606c52SThierry Reding { 13dc606c52SThierry Reding return container_of(rstc, struct tegra_bpmp, rstc); 14dc606c52SThierry Reding } 15dc606c52SThierry Reding 16dc606c52SThierry Reding static int tegra_bpmp_reset_common(struct reset_controller_dev *rstc, 17dc606c52SThierry Reding enum mrq_reset_commands command, 18dc606c52SThierry Reding unsigned int id) 19dc606c52SThierry Reding { 20dc606c52SThierry Reding struct tegra_bpmp *bpmp = to_tegra_bpmp(rstc); 21dc606c52SThierry Reding struct mrq_reset_request request; 22dc606c52SThierry Reding struct tegra_bpmp_message msg; 23dc606c52SThierry Reding 24dc606c52SThierry Reding memset(&request, 0, sizeof(request)); 25dc606c52SThierry Reding request.cmd = command; 26dc606c52SThierry Reding request.reset_id = id; 27dc606c52SThierry Reding 28dc606c52SThierry Reding memset(&msg, 0, sizeof(msg)); 29dc606c52SThierry Reding msg.mrq = MRQ_RESET; 30dc606c52SThierry Reding msg.tx.data = &request; 31dc606c52SThierry Reding msg.tx.size = sizeof(request); 32dc606c52SThierry Reding 33dc606c52SThierry Reding return tegra_bpmp_transfer(bpmp, &msg); 34dc606c52SThierry Reding } 35dc606c52SThierry Reding 36dc606c52SThierry Reding static int tegra_bpmp_reset_module(struct reset_controller_dev *rstc, 37dc606c52SThierry Reding unsigned long id) 38dc606c52SThierry Reding { 39dc606c52SThierry Reding return tegra_bpmp_reset_common(rstc, CMD_RESET_MODULE, id); 40dc606c52SThierry Reding } 41dc606c52SThierry Reding 42dc606c52SThierry Reding static int tegra_bpmp_reset_assert(struct reset_controller_dev *rstc, 43dc606c52SThierry Reding unsigned long id) 44dc606c52SThierry Reding { 45dc606c52SThierry Reding return tegra_bpmp_reset_common(rstc, CMD_RESET_ASSERT, id); 46dc606c52SThierry Reding } 47dc606c52SThierry Reding 48dc606c52SThierry Reding static int tegra_bpmp_reset_deassert(struct reset_controller_dev *rstc, 49dc606c52SThierry Reding unsigned long id) 50dc606c52SThierry Reding { 51dc606c52SThierry Reding return tegra_bpmp_reset_common(rstc, CMD_RESET_DEASSERT, id); 52dc606c52SThierry Reding } 53dc606c52SThierry Reding 54dc606c52SThierry Reding static const struct reset_control_ops tegra_bpmp_reset_ops = { 55dc606c52SThierry Reding .reset = tegra_bpmp_reset_module, 56dc606c52SThierry Reding .assert = tegra_bpmp_reset_assert, 57dc606c52SThierry Reding .deassert = tegra_bpmp_reset_deassert, 58dc606c52SThierry Reding }; 59dc606c52SThierry Reding 60dc606c52SThierry Reding int tegra_bpmp_init_resets(struct tegra_bpmp *bpmp) 61dc606c52SThierry Reding { 62dc606c52SThierry Reding bpmp->rstc.ops = &tegra_bpmp_reset_ops; 63dc606c52SThierry Reding bpmp->rstc.owner = THIS_MODULE; 64dc606c52SThierry Reding bpmp->rstc.of_node = bpmp->dev->of_node; 65dc606c52SThierry Reding bpmp->rstc.nr_resets = bpmp->soc->num_resets; 66dc606c52SThierry Reding 67dc606c52SThierry Reding return devm_reset_controller_register(bpmp->dev, &bpmp->rstc); 68dc606c52SThierry Reding } 69