1 /*
2 * Arm SCP/MCP Software
3 * Copyright (c) 2019-2022, Arm Limited and Contributors. All rights reserved.
4 *
5 * SPDX-License-Identifier: BSD-3-Clause
6 */
7
8 #include <internal/fwk_module.h>
9
10 #include <fwk_event.h>
11 #include <fwk_id.h>
12 #include <fwk_interrupt.h>
13 #include <fwk_list.h>
14 #include <fwk_log.h>
15 #include <fwk_module.h>
16 #include <fwk_status.h>
17
18 #include <stdbool.h>
19 #include <stddef.h>
20 #include <stdint.h>
21
22 static const char err_msg_func[] = "[FWK] Error %d in %s";
23
24 /*
25 * Static functions
26 */
check_api_call(fwk_id_t id,void * data)27 static int check_api_call(fwk_id_t id, void *data)
28 {
29 if (fwk_is_interrupt_context()) {
30 return FWK_E_ACCESS;
31 }
32
33 if ((!fwk_module_is_valid_entity_id(id)) || (data == NULL)) {
34 return FWK_E_PARAM;
35 }
36
37 return FWK_SUCCESS;
38 }
39
40 /*
41 * Internal interface functions for use by framework only
42 */
__fwk_get_delayed_response_list(fwk_id_t id)43 struct fwk_slist *__fwk_get_delayed_response_list(fwk_id_t id)
44 {
45 if (fwk_id_is_type(id, FWK_ID_TYPE_MODULE)) {
46 return &fwk_module_get_ctx(id)->delayed_response_list;
47 }
48
49 return &fwk_module_get_element_ctx(id)->delayed_response_list;
50 }
51
__fwk_search_delayed_response(fwk_id_t id,uint32_t cookie)52 struct fwk_event *__fwk_search_delayed_response(fwk_id_t id, uint32_t cookie)
53 {
54 struct fwk_slist *delayed_response_list;
55 struct fwk_slist_node *delayed_response_node;
56
57 delayed_response_list = __fwk_get_delayed_response_list(id);
58 delayed_response_node = fwk_list_head(delayed_response_list);
59
60 while (delayed_response_node != NULL) {
61 struct fwk_event *delayed_response;
62
63 delayed_response =
64 FWK_LIST_GET(delayed_response_node, struct fwk_event, slist_node);
65 if (delayed_response->cookie == cookie) {
66 return delayed_response;
67 }
68
69 delayed_response_node =
70 fwk_list_next(delayed_response_list, delayed_response_node);
71 }
72
73 return NULL;
74 }
75
76 /*
77 * Public Interface functions for use by Modules
78 */
fwk_get_delayed_response(fwk_id_t id,uint32_t cookie,struct fwk_event * event)79 int fwk_get_delayed_response(
80 fwk_id_t id,
81 uint32_t cookie,
82 struct fwk_event *event)
83 {
84 int status;
85 struct fwk_event *delayed_response;
86
87 status = check_api_call(id, event);
88 if (status != FWK_SUCCESS) {
89 goto error;
90 }
91
92 delayed_response = __fwk_search_delayed_response(id, cookie);
93 if (delayed_response == NULL) {
94 status = FWK_E_PARAM;
95 goto error;
96 }
97
98 *event = *delayed_response;
99
100 return FWK_SUCCESS;
101
102 error:
103 FWK_LOG_CRIT(err_msg_func, status, __func__);
104 return status;
105 }
106
fwk_is_delayed_response_list_empty(fwk_id_t id,bool * is_empty)107 int fwk_is_delayed_response_list_empty(fwk_id_t id, bool *is_empty)
108 {
109 int status;
110 struct fwk_slist *delayed_response_list;
111 struct fwk_slist_node *delayed_response_node;
112
113 status = check_api_call(id, is_empty);
114 if (status != FWK_SUCCESS) {
115 goto error;
116 }
117
118 delayed_response_list = __fwk_get_delayed_response_list(id);
119 delayed_response_node = fwk_list_head(delayed_response_list);
120
121 *is_empty = (delayed_response_node == NULL);
122
123 return FWK_SUCCESS;
124
125 error:
126 FWK_LOG_CRIT(err_msg_func, status, __func__);
127 return status;
128 }
129
fwk_get_first_delayed_response(fwk_id_t id,struct fwk_event * event)130 int fwk_get_first_delayed_response(fwk_id_t id, struct fwk_event *event)
131 {
132 int status;
133 struct fwk_slist *delayed_response_list;
134 struct fwk_slist_node *delayed_response_node;
135
136 status = check_api_call(id, event);
137 if (status != FWK_SUCCESS) {
138 goto error;
139 }
140
141 delayed_response_list = __fwk_get_delayed_response_list(id);
142 delayed_response_node = fwk_list_head(delayed_response_list);
143
144 if (delayed_response_node != NULL) {
145 *event = *(
146 FWK_LIST_GET(delayed_response_node, struct fwk_event, slist_node));
147 } else {
148 return FWK_E_STATE;
149 }
150
151 return FWK_SUCCESS;
152
153 error:
154 FWK_LOG_CRIT(err_msg_func, status, __func__);
155 return status;
156 }
157