1 /*
2  * SPDX-FileCopyrightText: 2015-2024 Espressif Systems (Shanghai) CO LTD
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 #include "esp_private/wifi.h"
8 #include "soc/soc_caps.h"
9 #include "esp_attr.h"
10 #include "esp32/rom/ets_sys.h"
11 #include "esp_heap_adapter.h"
12 #include "esp_timer.h"
13 #include "soc/rtc.h"
14 #include "esp_private/esp_clk.h"
15 #include "private/esp_coexist_adapter.h"
16 
17 #include <zephyr/logging/log.h>
18 LOG_MODULE_REGISTER(esp32_coex_adapter, CONFIG_WIFI_LOG_LEVEL);
19 
20 #define OSI_FUNCS_TIME_BLOCKING 0xffffffff
21 
esp_wifi_free(void * mem)22 void esp_wifi_free(void *mem)
23 {
24 	esp_wifi_free_func(mem);
25 }
26 
esp_coex_common_env_is_chip_wrapper(void)27 bool IRAM_ATTR esp_coex_common_env_is_chip_wrapper(void)
28 {
29 #ifdef CONFIG_IDF_ENV_FPGA
30 	return false;
31 #else
32 	return true;
33 #endif
34 }
35 
esp_coex_common_spin_lock_create_wrapper(void)36 void *esp_coex_common_spin_lock_create_wrapper(void)
37 {
38 	unsigned int *wifi_spin_lock = (unsigned int *)wifi_malloc(sizeof(unsigned int));
39 	if (wifi_spin_lock == NULL) {
40 		LOG_ERR("spin_lock_create_wrapper allocation failed");
41 	}
42 
43 	return (void *)wifi_spin_lock;
44 }
45 
esp_coex_common_int_disable_wrapper(void * wifi_int_mux)46 uint32_t IRAM_ATTR esp_coex_common_int_disable_wrapper(void *wifi_int_mux)
47 {
48 	unsigned int *int_mux = (unsigned int *)wifi_int_mux;
49 
50 	*int_mux = irq_lock();
51 	return 0;
52 }
53 
esp_coex_common_int_restore_wrapper(void * wifi_int_mux,uint32_t tmp)54 void IRAM_ATTR esp_coex_common_int_restore_wrapper(void *wifi_int_mux, uint32_t tmp)
55 {
56 	unsigned int *key = (unsigned int *)wifi_int_mux;
57 
58 	irq_unlock(*key);
59 }
60 
esp_coex_common_task_yield_from_isr_wrapper(void)61 void IRAM_ATTR esp_coex_common_task_yield_from_isr_wrapper(void)
62 {
63 	k_yield();
64 }
65 
esp_coex_common_semphr_create_wrapper(uint32_t max,uint32_t init)66 void *esp_coex_common_semphr_create_wrapper(uint32_t max, uint32_t init)
67 {
68 	struct k_sem *sem = (struct k_sem *)wifi_malloc(sizeof(struct k_sem));
69 
70 	if (sem == NULL) {
71 		LOG_ERR("semphr_create_wrapper allocation failed");
72 	}
73 
74 	k_sem_init(sem, init, max);
75 
76 	return (void *)sem;
77 }
78 
esp_coex_common_semphr_delete_wrapper(void * semphr)79 void esp_coex_common_semphr_delete_wrapper(void *semphr)
80 {
81 	esp_wifi_free(semphr);
82 }
83 
esp_coex_common_semphr_take_wrapper(void * semphr,uint32_t block_time_tick)84 int32_t esp_coex_common_semphr_take_wrapper(void *semphr, uint32_t block_time_tick)
85 {
86 	if (block_time_tick == OSI_FUNCS_TIME_BLOCKING) {
87 		int ret = k_sem_take((struct k_sem *)semphr, K_FOREVER);
88 		if (ret == 0) {
89 			return 1;
90 		}
91 	} else {
92 		int ret = k_sem_take((struct k_sem *)semphr, K_TICKS(block_time_tick));
93 
94 		if (ret == 0) {
95 			return 1;
96 		}
97 	}
98 	return 0;
99 }
100 
esp_coex_common_semphr_give_wrapper(void * semphr)101 int32_t esp_coex_common_semphr_give_wrapper(void *semphr)
102 {
103 	k_sem_give((struct k_sem *)semphr);
104 	return 1;
105 }
106 
esp_coex_common_timer_disarm_wrapper(void * timer)107 void IRAM_ATTR esp_coex_common_timer_disarm_wrapper(void *timer)
108 {
109 	ets_timer_disarm(timer);
110 }
111 
esp_coex_common_timer_done_wrapper(void * ptimer)112 void esp_coex_common_timer_done_wrapper(void *ptimer)
113 {
114 	ets_timer_done(ptimer);
115 }
116 
esp_coex_common_timer_setfn_wrapper(void * ptimer,void * pfunction,void * parg)117 void esp_coex_common_timer_setfn_wrapper(void *ptimer, void *pfunction, void *parg)
118 {
119 	ets_timer_setfn(ptimer, pfunction, parg);
120 }
121 
esp_coex_common_timer_arm_us_wrapper(void * ptimer,uint32_t us,bool repeat)122 void IRAM_ATTR esp_coex_common_timer_arm_us_wrapper(void *ptimer, uint32_t us, bool repeat)
123 {
124 	ets_timer_arm_us(ptimer, us, repeat);
125 }
126 
esp_coex_common_malloc_internal_wrapper(size_t size)127 void *IRAM_ATTR esp_coex_common_malloc_internal_wrapper(size_t size)
128 {
129 	return wifi_malloc(size);
130 }
131 
esp_coex_internal_semphr_take_from_isr_wrapper(void * semphr,void * hptw)132 static int32_t IRAM_ATTR esp_coex_internal_semphr_take_from_isr_wrapper(void *semphr, void *hptw)
133 {
134 	int *hpt = (int *)hptw;
135 
136 	int ret = k_sem_take((struct k_sem *)semphr, K_NO_WAIT);
137 
138 	if (ret == 0) {
139 		return 1;
140 	}
141 
142 	*hpt = 0;
143 	return 0;
144 }
145 
esp_coex_internal_semphr_give_from_isr_wrapper(void * semphr,void * hptw)146 static int32_t IRAM_ATTR esp_coex_internal_semphr_give_from_isr_wrapper(void *semphr, void *hptw)
147 {
148 	int *hpt = (int *)hptw;
149 
150 	k_sem_give((struct k_sem *)semphr);
151 
152 	*hpt = 0;
153 	return 0;
154 }
155 
esp_coexist_debug_matrix_init_wrapper(int evt,int sig,bool rev)156 static int esp_coexist_debug_matrix_init_wrapper(int evt, int sig, bool rev)
157 {
158 #if CONFIG_ESP_COEX_GPIO_DEBUG
159 	return esp_coexist_debug_matrix_init(evt, sig, rev);
160 #else
161 	return ESP_ERR_NOT_SUPPORTED;
162 #endif
163 }
164 
esp_coex_is_in_isr_wrapper(void)165 int32_t IRAM_ATTR esp_coex_is_in_isr_wrapper(void)
166 {
167 	return k_is_in_isr();
168 }
169 
170 coex_adapter_funcs_t g_coex_adapter_funcs = {
171 	._version = COEX_ADAPTER_VERSION,
172 	._spin_lock_create = esp_coex_common_spin_lock_create_wrapper,
173 	._spin_lock_delete = esp_wifi_free,
174 	._int_disable = esp_coex_common_int_disable_wrapper,
175 	._int_enable = esp_coex_common_int_restore_wrapper,
176 	._task_yield_from_isr = esp_coex_common_task_yield_from_isr_wrapper,
177 	._semphr_create = esp_coex_common_semphr_create_wrapper,
178 	._semphr_delete = esp_coex_common_semphr_delete_wrapper,
179 	._semphr_take_from_isr = esp_coex_internal_semphr_take_from_isr_wrapper,
180 	._semphr_give_from_isr = esp_coex_internal_semphr_give_from_isr_wrapper,
181 	._semphr_take = esp_coex_common_semphr_take_wrapper,
182 	._semphr_give = esp_coex_common_semphr_give_wrapper,
183 	._is_in_isr = esp_coex_is_in_isr_wrapper,
184 	._malloc_internal = esp_coex_common_malloc_internal_wrapper,
185 	._free = esp_wifi_free,
186 	._esp_timer_get_time = esp_timer_get_time,
187 	._timer_disarm = esp_coex_common_timer_disarm_wrapper,
188 	._timer_done = esp_coex_common_timer_done_wrapper,
189 	._timer_setfn = esp_coex_common_timer_setfn_wrapper,
190 	._timer_arm_us = esp_coex_common_timer_arm_us_wrapper,
191 	._debug_matrix_init = esp_coexist_debug_matrix_init_wrapper,
192 	._magic = COEX_ADAPTER_MAGIC,
193 };
194