xref: /optee_os/core/drivers/gpio/gpio.c (revision 4fc179b6919181df142772f53cc26cd107fed69f)
1*4fc179b6SThomas Perrot // SPDX-License-Identifier: BSD-2-Clause
2*4fc179b6SThomas Perrot /*
3*4fc179b6SThomas Perrot  * Copyright (c) 2022, Microchip
4*4fc179b6SThomas Perrot  */
5*4fc179b6SThomas Perrot 
6*4fc179b6SThomas Perrot #include <drivers/gpio.h>
7*4fc179b6SThomas Perrot #include <libfdt.h>
8*4fc179b6SThomas Perrot #include <stdio.h>
9*4fc179b6SThomas Perrot #include <tee_api_defines.h>
10*4fc179b6SThomas Perrot #include <tee_api_defines_extensions.h>
11*4fc179b6SThomas Perrot #include <tee_api_types.h>
12*4fc179b6SThomas Perrot #include <util.h>
13*4fc179b6SThomas Perrot 
14*4fc179b6SThomas Perrot struct gpio *gpio_dt_alloc_pin(struct dt_driver_phandle_args *a,
15*4fc179b6SThomas Perrot 			       TEE_Result *res)
16*4fc179b6SThomas Perrot {
17*4fc179b6SThomas Perrot 	struct gpio *gpio = NULL;
18*4fc179b6SThomas Perrot 
19*4fc179b6SThomas Perrot 	if (a->args_count != 2) {
20*4fc179b6SThomas Perrot 		*res = TEE_ERROR_BAD_PARAMETERS;
21*4fc179b6SThomas Perrot 		return NULL;
22*4fc179b6SThomas Perrot 	}
23*4fc179b6SThomas Perrot 
24*4fc179b6SThomas Perrot 	gpio = calloc(1, sizeof(struct gpio));
25*4fc179b6SThomas Perrot 	if (!gpio) {
26*4fc179b6SThomas Perrot 		*res = TEE_ERROR_OUT_OF_MEMORY;
27*4fc179b6SThomas Perrot 		return NULL;
28*4fc179b6SThomas Perrot 	}
29*4fc179b6SThomas Perrot 
30*4fc179b6SThomas Perrot 	gpio->pin = a->args[0];
31*4fc179b6SThomas Perrot 	gpio->dt_flags = a->args[1];
32*4fc179b6SThomas Perrot 
33*4fc179b6SThomas Perrot 	*res = TEE_SUCCESS;
34*4fc179b6SThomas Perrot 	return gpio;
35*4fc179b6SThomas Perrot }
36*4fc179b6SThomas Perrot 
37*4fc179b6SThomas Perrot static char *gpio_get_dt_prop_name(const char *gpio_name)
38*4fc179b6SThomas Perrot {
39*4fc179b6SThomas Perrot 	char *prop_name = NULL;
40*4fc179b6SThomas Perrot 	int max_len = strlen(gpio_name) + strlen("-gpios") + 1;
41*4fc179b6SThomas Perrot 
42*4fc179b6SThomas Perrot 	prop_name = calloc(1, max_len);
43*4fc179b6SThomas Perrot 	if (!prop_name)
44*4fc179b6SThomas Perrot 		return NULL;
45*4fc179b6SThomas Perrot 
46*4fc179b6SThomas Perrot 	snprintf(prop_name, max_len, "%s-gpios", gpio_name);
47*4fc179b6SThomas Perrot 
48*4fc179b6SThomas Perrot 	return prop_name;
49*4fc179b6SThomas Perrot }
50*4fc179b6SThomas Perrot 
51*4fc179b6SThomas Perrot TEE_Result gpio_dt_get_by_index(const void *fdt, int nodeoffset,
52*4fc179b6SThomas Perrot 				unsigned int index, const char *gpio_name,
53*4fc179b6SThomas Perrot 				struct gpio **gpio)
54*4fc179b6SThomas Perrot {
55*4fc179b6SThomas Perrot 	TEE_Result res = TEE_ERROR_GENERIC;
56*4fc179b6SThomas Perrot 	char *prop_name = NULL;
57*4fc179b6SThomas Perrot 
58*4fc179b6SThomas Perrot 	prop_name = gpio_get_dt_prop_name(gpio_name);
59*4fc179b6SThomas Perrot 	if (!prop_name)
60*4fc179b6SThomas Perrot 		return TEE_ERROR_OUT_OF_MEMORY;
61*4fc179b6SThomas Perrot 
62*4fc179b6SThomas Perrot 	*gpio = dt_driver_device_from_node_idx_prop(prop_name, fdt, nodeoffset,
63*4fc179b6SThomas Perrot 						    index, DT_DRIVER_GPIO,
64*4fc179b6SThomas Perrot 						    &res);
65*4fc179b6SThomas Perrot 	free(prop_name);
66*4fc179b6SThomas Perrot 
67*4fc179b6SThomas Perrot 	return res;
68*4fc179b6SThomas Perrot }
69