blob: 5383d09896986f6ffd418f7ca8e9ebfb3aff6ef1 [file] [log] [blame]
Michal Simek0fd9f362022-02-07 10:27:37 +01001// SPDX-License-Identifier: GPL-2.0
2/*
3 * Copyright (c) 2021, Xilinx. Inc.
4 */
5
6#include <common.h>
7#include <dm.h>
8#include <log.h>
9#include <malloc.h>
10#include <misc.h>
11#include <power-domain-uclass.h>
12#include <linux/bitops.h>
13
14#include <zynqmp_firmware.h>
15
16#define NODE_ID_LOCATION 5
17
18static unsigned int xpm_configobject[] = {
19 /* HEADER */
20 2, /* Number of remaining words in the header */
21 1, /* Number of sections included in config object */
22 PM_CONFIG_OBJECT_TYPE_OVERLAY, /* Type of Config object as overlay */
23 /* SLAVE SECTION */
24
25 PM_CONFIG_SLAVE_SECTION_ID, /* Section ID */
26 1, /* Number of slaves */
27
28 0, /* Node ID which will be changed below */
29 PM_SLAVE_FLAG_IS_SHAREABLE,
30 PM_CONFIG_IPI_PSU_CORTEXA53_0_MASK |
31 PM_CONFIG_IPI_PSU_CORTEXR5_0_MASK |
32 PM_CONFIG_IPI_PSU_CORTEXR5_1_MASK, /* IPI Mask */
33};
34
35static int zynqmp_pm_request_node(const u32 node, const u32 capabilities,
36 const u32 qos, const enum zynqmp_pm_request_ack ack)
37{
38 return xilinx_pm_request(PM_REQUEST_NODE, node, capabilities,
39 qos, ack, NULL);
40}
41
42static int zynqmp_power_domain_request(struct power_domain *power_domain)
43{
44 /* Record power domain id */
45 xpm_configobject[NODE_ID_LOCATION] = power_domain->id;
46
47 zynqmp_pmufw_load_config_object(xpm_configobject, sizeof(xpm_configobject));
48
49 return 0;
50}
51
52static int zynqmp_power_domain_free(struct power_domain *power_domain)
53{
54 /* nop now */
55 return 0;
56}
57
58static int zynqmp_power_domain_on(struct power_domain *power_domain)
59{
60 return zynqmp_pm_request_node(power_domain->id,
61 ZYNQMP_PM_CAPABILITY_ACCESS,
62 ZYNQMP_PM_MAX_QOS,
63 ZYNQMP_PM_REQUEST_ACK_BLOCKING);
64}
65
66static int zynqmp_power_domain_off(struct power_domain *power_domain)
67{
68 /* nop now */
69 return 0;
70}
71
72struct power_domain_ops zynqmp_power_domain_ops = {
73 .request = zynqmp_power_domain_request,
74 .rfree = zynqmp_power_domain_free,
75 .on = zynqmp_power_domain_on,
76 .off = zynqmp_power_domain_off,
77};
78
79static int zynqmp_power_domain_probe(struct udevice *dev)
80{
81 return 0;
82}
83
84U_BOOT_DRIVER(zynqmp_power_domain) = {
85 .name = "zynqmp_power_domain",
86 .id = UCLASS_POWER_DOMAIN,
87 .probe = zynqmp_power_domain_probe,
88 .ops = &zynqmp_power_domain_ops,
89};