1 /*
2 * SPDX-FileCopyrightText: 2023-2024 Espressif Systems (Shanghai) CO LTD
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 */
6 #pragma once
7
8 #include <stdbool.h>
9 #include <string.h>
10 #include "hal/assert.h"
11 #include "hal/ecc_types.h"
12 #include "soc/ecc_mult_reg.h"
13 #include "soc/pcr_struct.h"
14 #include "soc/pcr_reg.h"
15
16 #ifdef __cplusplus
17 extern "C" {
18 #endif
19
20 typedef enum {
21 ECC_PARAM_PX = 0x0,
22 ECC_PARAM_PY,
23 ECC_PARAM_K,
24 ECC_PARAM_QX,
25 ECC_PARAM_QY,
26 ECC_PARAM_QZ,
27 } ecc_ll_param_t;
28
ecc_ll_power_up(void)29 static inline void ecc_ll_power_up(void)
30 {
31 REG_CLR_BIT(PCR_ECC_PD_CTRL_REG, PCR_ECC_MEM_PD);
32 REG_CLR_BIT(PCR_ECC_PD_CTRL_REG, PCR_ECC_MEM_FORCE_PD);
33 }
34
ecc_ll_power_down(void)35 static inline void ecc_ll_power_down(void)
36 {
37 REG_CLR_BIT(PCR_ECC_PD_CTRL_REG, PCR_ECC_MEM_FORCE_PU);
38 REG_SET_BIT(PCR_ECC_PD_CTRL_REG, PCR_ECC_MEM_PD);
39 }
40
ecc_ll_enable_interrupt(void)41 static inline void ecc_ll_enable_interrupt(void)
42 {
43 REG_SET_FIELD(ECC_MULT_INT_ENA_REG, ECC_MULT_CALC_DONE_INT_ENA, 1);
44 }
45
ecc_ll_disable_interrupt(void)46 static inline void ecc_ll_disable_interrupt(void)
47 {
48 REG_SET_FIELD(ECC_MULT_INT_ENA_REG, ECC_MULT_CALC_DONE_INT_ENA, 0);
49 }
50
ecc_ll_clear_interrupt(void)51 static inline void ecc_ll_clear_interrupt(void)
52 {
53 REG_SET_FIELD(ECC_MULT_INT_CLR_REG, ECC_MULT_CALC_DONE_INT_CLR, 1);
54 }
55
ecc_ll_set_mode(ecc_mode_t mode)56 static inline void ecc_ll_set_mode(ecc_mode_t mode)
57 {
58 switch(mode) {
59 case ECC_MODE_POINT_MUL:
60 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 0);
61 break;
62 case ECC_MODE_VERIFY:
63 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 2);
64 break;
65 case ECC_MODE_VERIFY_THEN_POINT_MUL:
66 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 3);
67 break;
68 case ECC_MODE_JACOBIAN_POINT_MUL:
69 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 4);
70 break;
71 case ECC_MODE_POINT_ADD:
72 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 5);
73 break;
74 case ECC_MODE_JACOBIAN_POINT_VERIFY:
75 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 6);
76 break;
77 case ECC_MODE_POINT_VERIFY_JACOBIAN_MUL:
78 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 7);
79 break;
80 case ECC_MODE_MOD_ADD:
81 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 8);
82 break;
83 case ECC_MODE_MOD_SUB:
84 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 9);
85 break;
86 case ECC_MODE_MOD_MUL:
87 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 10);
88 break;
89 case ECC_MODE_INVERSE_MUL:
90 REG_SET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE, 11);
91 break;
92 default:
93 HAL_ASSERT(false && "Unsupported mode");
94 break;
95 }
96 }
97
ecc_ll_set_curve(ecc_curve_t curve)98 static inline void ecc_ll_set_curve(ecc_curve_t curve)
99 {
100 switch(curve) {
101 case ECC_CURVE_SECP256R1:
102 REG_SET_BIT(ECC_MULT_CONF_REG, ECC_MULT_KEY_LENGTH);
103 break;
104 case ECC_CURVE_SECP192R1:
105 REG_CLR_BIT(ECC_MULT_CONF_REG, ECC_MULT_KEY_LENGTH);
106 break;
107 default:
108 HAL_ASSERT(false && "Unsupported curve");
109 return;
110 }
111 }
112
ecc_ll_set_mod_base(ecc_mod_base_t base)113 static inline void ecc_ll_set_mod_base(ecc_mod_base_t base)
114 {
115 switch(base) {
116 case ECC_MOD_N:
117 REG_CLR_BIT(ECC_MULT_CONF_REG, ECC_MULT_MOD_BASE);
118 break;
119 case ECC_MOD_P:
120 REG_SET_BIT(ECC_MULT_CONF_REG, ECC_MULT_MOD_BASE);
121 break;
122 default:
123 HAL_ASSERT(false && "Unsupported curve");
124 return;
125 }
126 }
127
ecc_ll_write_param(ecc_ll_param_t param,const uint8_t * buf,uint16_t len)128 static inline void ecc_ll_write_param(ecc_ll_param_t param, const uint8_t *buf, uint16_t len)
129 {
130 uint32_t reg;
131 uint32_t word;
132 switch (param) {
133 case ECC_PARAM_PX:
134 reg = ECC_MULT_PX_MEM;
135 break;
136 case ECC_PARAM_PY:
137 reg = ECC_MULT_PY_MEM;
138 break;
139 case ECC_PARAM_K:
140 reg = ECC_MULT_K_MEM;
141 break;
142 case ECC_PARAM_QX:
143 reg = ECC_MULT_QX_MEM;
144 break;
145 case ECC_PARAM_QY:
146 reg = ECC_MULT_QY_MEM;
147 break;
148 case ECC_PARAM_QZ:
149 reg = ECC_MULT_QZ_MEM;
150 break;
151 default:
152 HAL_ASSERT(false && "Invalid parameter");
153 return;
154 }
155
156 for (int i = 0; i < len; i += 4) {
157 memcpy(&word, buf + i, 4);
158 REG_WRITE(reg + i, word);
159 }
160 }
161
ecc_ll_start_calc(void)162 static inline void ecc_ll_start_calc(void)
163 {
164 REG_SET_BIT(ECC_MULT_CONF_REG, ECC_MULT_START);
165 }
166
ecc_ll_is_calc_finished(void)167 static inline int ecc_ll_is_calc_finished(void)
168 {
169 return REG_GET_FIELD(ECC_MULT_INT_RAW_REG, ECC_MULT_CALC_DONE_INT_RAW);
170 }
171
ecc_ll_get_mode(void)172 static inline ecc_mode_t ecc_ll_get_mode(void)
173 {
174 return REG_GET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_WORK_MODE);
175 }
176
ecc_ll_get_verification_result(void)177 static inline int ecc_ll_get_verification_result(void)
178 {
179 return REG_GET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_VERIFICATION_RESULT);
180 }
181
ecc_ll_get_curve(void)182 static inline ecc_curve_t ecc_ll_get_curve(void)
183 {
184 return REG_GET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_KEY_LENGTH);
185 }
186
ecc_ll_get_mod_base(void)187 static inline ecc_mod_base_t ecc_ll_get_mod_base(void)
188 {
189 return REG_GET_FIELD(ECC_MULT_CONF_REG, ECC_MULT_MOD_BASE);
190 }
191
ecc_ll_read_param(ecc_ll_param_t param,uint8_t * buf,uint16_t len)192 static inline void ecc_ll_read_param(ecc_ll_param_t param, uint8_t *buf, uint16_t len)
193 {
194 uint32_t reg;
195 switch (param) {
196 case ECC_PARAM_PX:
197 reg = ECC_MULT_PX_MEM;
198 break;
199 case ECC_PARAM_PY:
200 reg = ECC_MULT_PY_MEM;
201 break;
202 case ECC_PARAM_K:
203 reg = ECC_MULT_K_MEM;
204 break;
205 case ECC_PARAM_QX:
206 reg = ECC_MULT_QX_MEM;
207 break;
208 case ECC_PARAM_QY:
209 reg = ECC_MULT_QY_MEM;
210 break;
211 case ECC_PARAM_QZ:
212 reg = ECC_MULT_QZ_MEM;
213 break;
214 default:
215 HAL_ASSERT(false && "Invalid parameter");
216 return;
217 }
218
219 memcpy(buf, (void *)reg, len);
220 }
221
222 #ifdef __cplusplus
223 }
224 #endif
225