power: zynqmp: Add power domain driver for ZynqMP

Driver should be enabled by CONFIG_POWER_DOMAIN=y and
CONFIG_ZYNQMP_POWER_DOMAIN=y. Power domain driver doesn't have own DT node
but it uses zynqmp firmware DT node that's why there is a need to bind
driver when firmware node is found.

Driver itself is simple. It is sending pmufw config object overlay for
enabling access to device which is done in ...domain_request().
In ...domain_on() capabilities are passed and node is requested.
This should be bare minimum of required to get power domain driver working.

Signed-off-by: Michal Simek <michal.simek@xilinx.com>
Reviewed-by: Jaehoon Chung <jh80.chung@samsung.com>
Link: https://lore.kernel.org/r/f4b9433b91c0b18c375b061c7a4e29d428f70547.1644226055.git.michal.simek@xilinx.com
diff --git a/drivers/firmware/firmware-zynqmp.c b/drivers/firmware/firmware-zynqmp.c
index 839203e..8d78888 100644
--- a/drivers/firmware/firmware-zynqmp.c
+++ b/drivers/firmware/firmware-zynqmp.c
@@ -8,6 +8,7 @@
 #include <common.h>
 #include <cpu_func.h>
 #include <dm.h>
+#include <dm/lists.h>
 #include <log.h>
 #include <zynqmp_firmware.h>
 #include <asm/cache.h>
@@ -226,8 +227,27 @@
 	{ }
 };
 
+static int zynqmp_firmware_bind(struct udevice *dev)
+{
+	int ret;
+	struct udevice *child;
+
+	if (IS_ENABLED(CONFIG_ZYNQMP_POWER_DOMAIN)) {
+		ret = device_bind_driver_to_node(dev, "zynqmp_power_domain",
+						 "zynqmp_power_domain",
+						 dev_ofnode(dev), &child);
+		if (ret) {
+			printf("zynqmp power domain driver is not bound: %d\n", ret);
+			return ret;
+		}
+	}
+
+	return dm_scan_fdt_dev(dev);
+}
+
 U_BOOT_DRIVER(zynqmp_firmware) = {
 	.id = UCLASS_FIRMWARE,
 	.name = "zynqmp_firmware",
 	.of_match = zynqmp_firmware_ids,
+	.bind = zynqmp_firmware_bind,
 };