efm32gg11_crypto_pkc.c
Go to the documentation of this file.
1 /**
2  * @file efm32gg11_crypto_pkc.c
3  * @brief EFM32 Giant Gecko 11 public-key hardware accelerator
4  *
5  * @section License
6  *
7  * SPDX-License-Identifier: GPL-2.0-or-later
8  *
9  * Copyright (C) 2010-2025 Oryx Embedded SARL. All rights reserved.
10  *
11  * This file is part of CycloneCRYPTO Open.
12  *
13  * This program is free software; you can redistribute it and/or
14  * modify it under the terms of the GNU General Public License
15  * as published by the Free Software Foundation; either version 2
16  * of the License, or (at your option) any later version.
17  *
18  * This program is distributed in the hope that it will be useful,
19  * but WITHOUT ANY WARRANTY; without even the implied warranty of
20  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21  * GNU General Public License for more details.
22  *
23  * You should have received a copy of the GNU General Public License
24  * along with this program; if not, write to the Free Software Foundation,
25  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
26  *
27  * @author Oryx Embedded SARL (www.oryx-embedded.com)
28  * @version 2.5.0
29  **/
30 
31 //Switch to the appropriate trace level
32 #define TRACE_LEVEL CRYPTO_TRACE_LEVEL
33 
34 //Dependencies
35 #include "em_device.h"
36 #include "em_crypto.h"
37 #include "core/crypto.h"
40 #include "ecc/ec.h"
41 #include "ecc/ec_misc.h"
42 #include "debug.h"
43 
44 //Check crypto library configuration
45 #if (EFM32GG11_CRYPTO_PKC_SUPPORT == ENABLED)
46 #if (EC_SUPPORT == ENABLED)
47 
48 /**
49  * @brief Modular multiplication
50  * @param[in] curve Elliptic curve parameters
51  * @param[out] r Resulting integer R = (A * B) mod p
52  * @param[in] a An integer such as 0 <= A < p
53  * @param[in] b An integer such as 0 <= B < p
54  **/
55 
56 void ecFieldMulMod(const EcCurve *curve, uint32_t *r, const uint32_t *a,
57  const uint32_t *b)
58 {
59  //Check elliptic curve
60  if(osStrcmp(curve->name, "secp256r1") == 0)
61  {
62  //Acquire exclusive access to the CRYPTO module
64 
65  //Set wide arithmetic configuration
66  CRYPTO0->WAC = 0;
67  CRYPTO0->CTRL = 0;
68 
69  //Set CRYPTO module parameters
70  CRYPTO_ModulusSet(CRYPTO0, cryptoModulusEccP256);
71  CRYPTO_MulOperandWidthSet(CRYPTO0, cryptoMulOperandModulusBits);
72  CRYPTO_ResultWidthSet(CRYPTO0, cryptoResult256Bits);
73 
74  //Copy the first operand
75  CRYPTO_DDataWrite(&CRYPTO0->DDATA1, a);
76 
77  //Copy the second operand
78  CRYPTO_DDataWrite(&CRYPTO0->DDATA2, b);
79 
80  //Compute R = (A * B) mod p
81  CRYPTO_EXECUTE_2(CRYPTO0,
82  CRYPTO_CMD_INSTR_SELDDATA0DDATA2,
83  CRYPTO_CMD_INSTR_MMUL);
84 
85  //Wait for the instruction sequence to complete
86  CRYPTO_InstructionSequenceWait(CRYPTO0);
87 
88  //Copy the resulting value
89  CRYPTO_DDataRead(&CRYPTO0->DDATA0, r);
90 
91  //Release exclusive access to the CRYPTO module
93  }
94  else
95  {
96  uint_t pLen;
97  uint32_t u[EC_MAX_MODULUS_SIZE * 2];
98 
99  //Get the length of the modulus, in words
100  pLen = (curve->fieldSize + 31) / 32;
101 
102  //Compute R = (A * B) mod p
103  ecScalarMul(u, u + pLen, a, b, pLen);
104  curve->fieldMod(curve, r, u);
105  }
106 }
107 
108 
109 /**
110  * @brief Modular squaring
111  * @param[in] curve Elliptic curve parameters
112  * @param[out] r Resulting integer R = A^2 mod p
113  * @param[in] a An integer such as 0 <= A < p
114  **/
115 
116 void ecFieldSqrMod(const EcCurve *curve, uint32_t *r, const uint32_t *a)
117 {
118  //Check elliptic curve
119  if(osStrcmp(curve->name, "secp256r1") == 0)
120  {
121  //Acquire exclusive access to the CRYPTO module
123 
124  //Set wide arithmetic configuration
125  CRYPTO0->WAC = 0;
126  CRYPTO0->CTRL = 0;
127 
128  //Set CRYPTO module parameters
129  CRYPTO_ModulusSet(CRYPTO0, cryptoModulusEccP256);
130  CRYPTO_MulOperandWidthSet(CRYPTO0, cryptoMulOperandModulusBits);
131  CRYPTO_ResultWidthSet(CRYPTO0, cryptoResult256Bits);
132 
133  //Copy the operand
134  CRYPTO_DDataWrite(&CRYPTO0->DDATA1, a);
135 
136  //Compute R = (A ^ 2) mod p
137  CRYPTO_EXECUTE_3(CRYPTO0,
138  CRYPTO_CMD_INSTR_DDATA1TODDATA2,
139  CRYPTO_CMD_INSTR_SELDDATA0DDATA2,
140  CRYPTO_CMD_INSTR_MMUL);
141 
142  //Wait for the instruction sequence to complete
143  CRYPTO_InstructionSequenceWait(CRYPTO0);
144 
145  //Copy the resulting value
146  CRYPTO_DDataRead(&CRYPTO0->DDATA0, r);
147 
148  //Release exclusive access to the CRYPTO module
150  }
151  else
152  {
153  uint_t pLen;
154  uint32_t u[EC_MAX_MODULUS_SIZE * 2];
155 
156  //Get the length of the modulus, in words
157  pLen = (curve->fieldSize + 31) / 32;
158 
159  //Compute R = (A ^ 2) mod p
160  ecScalarSqr(u, a, pLen);
161  curve->fieldMod(curve, r, u);
162  }
163 }
164 
165 
166 /**
167  * @brief Modular multiplication
168  * @param[in] curve Elliptic curve parameters
169  * @param[out] r Resulting integer R = (A * B) mod q
170  * @param[in] a An integer such as 0 <= A < q
171  * @param[in] b An integer such as 0 <= B < q
172  **/
173 
174 void ecScalarMulMod(const EcCurve *curve, uint32_t *r, const uint32_t *a,
175  const uint32_t *b)
176 {
177  //Check elliptic curve
178  if(osStrcmp(curve->name, "secp256r1") == 0)
179  {
180  //Acquire exclusive access to the CRYPTO module
182 
183  //Set wide arithmetic configuration
184  CRYPTO0->WAC = 0;
185  CRYPTO0->CTRL = 0;
186 
187  //Set CRYPTO module parameters
188  CRYPTO_ModulusSet(CRYPTO0, cryptoModulusEccP256Order);
189  CRYPTO_MulOperandWidthSet(CRYPTO0, cryptoMulOperandModulusBits);
190  CRYPTO_ResultWidthSet(CRYPTO0, cryptoResult256Bits);
191 
192  //Copy the first operand
193  CRYPTO_DDataWrite(&CRYPTO0->DDATA1, a);
194 
195  //Copy the second operand
196  CRYPTO_DDataWrite(&CRYPTO0->DDATA2, b);
197 
198  //Compute R = (A * B) mod q
199  CRYPTO_EXECUTE_2(CRYPTO0,
200  CRYPTO_CMD_INSTR_SELDDATA0DDATA2,
201  CRYPTO_CMD_INSTR_MMUL);
202 
203  //Wait for the instruction sequence to complete
204  CRYPTO_InstructionSequenceWait(CRYPTO0);
205 
206  //Copy the resulting value
207  CRYPTO_DDataRead(&CRYPTO0->DDATA0, r);
208 
209  //Release exclusive access to the CRYPTO module
211  }
212  else
213  {
214  uint_t qLen;
215  uint32_t u[EC_MAX_ORDER_SIZE * 2];
216 
217  //Get the length of the order, in words
218  qLen = (curve->orderSize + 31) / 32;
219 
220  //Compute R = (A * B) mod q
221  ecScalarMul(u, u + qLen, a, b, qLen);
222  curve->scalarMod(curve, r, u);
223  }
224 }
225 
226 
227 /**
228  * @brief Modular squaring
229  * @param[in] curve Elliptic curve parameters
230  * @param[out] r Resulting integer R = A^2 mod q
231  * @param[in] a An integer such as 0 <= A < q
232  **/
233 
234 void ecScalarSqrMod(const EcCurve *curve, uint32_t *r, const uint32_t *a)
235 {
236  //Check elliptic curve
237  if(osStrcmp(curve->name, "secp256r1") == 0)
238  {
239  //Acquire exclusive access to the CRYPTO module
241 
242  //Set wide arithmetic configuration
243  CRYPTO0->WAC = 0;
244  CRYPTO0->CTRL = 0;
245 
246  //Set CRYPTO module parameters
247  CRYPTO_ModulusSet(CRYPTO0, cryptoModulusEccP256Order);
248  CRYPTO_MulOperandWidthSet(CRYPTO0, cryptoMulOperandModulusBits);
249  CRYPTO_ResultWidthSet(CRYPTO0, cryptoResult256Bits);
250 
251  //Copy the operand
252  CRYPTO_DDataWrite(&CRYPTO0->DDATA1, a);
253 
254  //Compute R = (A ^ 2) mod q
255  CRYPTO_EXECUTE_3(CRYPTO0,
256  CRYPTO_CMD_INSTR_DDATA1TODDATA2,
257  CRYPTO_CMD_INSTR_SELDDATA0DDATA2,
258  CRYPTO_CMD_INSTR_MMUL);
259 
260  //Wait for the instruction sequence to complete
261  CRYPTO_InstructionSequenceWait(CRYPTO0);
262 
263  //Copy the resulting value
264  CRYPTO_DDataRead(&CRYPTO0->DDATA0, r);
265 
266  //Release exclusive access to the CRYPTO module
268  }
269  else
270  {
271  uint_t qLen;
272  uint32_t u[EC_MAX_ORDER_SIZE * 2];
273 
274  //Get the length of the order, in words
275  qLen = (curve->orderSize + 31) / 32;
276 
277  //Compute R = (A ^ 2) mod q
278  ecScalarSqr(u, a, qLen);
279  curve->scalarMod(curve, r, u);
280  }
281 }
282 
283 #endif
284 #endif
uint8_t b
Definition: nbns_common.h:104
__weak_func void ecScalarSqr(uint32_t *r, const uint32_t *a, uint_t n)
Squaring operation.
Definition: ec_misc.c:832
uint8_t a
Definition: ndp.h:411
void ecFieldSqrMod(const EcCurve *curve, uint32_t *r, const uint32_t *a)
Modular squaring.
#define EC_MAX_ORDER_SIZE
Definition: ec.h:315
void ecScalarSqrMod(const EcCurve *curve, uint32_t *r, const uint32_t *a)
Modular squaring.
#define osStrcmp(s1, s2)
Definition: os_port.h:174
EFM32 Giant Gecko 11 public-key hardware accelerator.
uint8_t r
Definition: ndp.h:346
void ecScalarMulMod(const EcCurve *curve, uint32_t *r, const uint32_t *a, const uint32_t *b)
Modular multiplication.
EFM32 Giant Gecko 11 hardware cryptographic accelerator.
Helper routines for ECC.
General definitions for cryptographic algorithms.
uint8_t u
Definition: lldp_ext_med.h:213
void osAcquireMutex(OsMutex *mutex)
Acquire ownership of the specified mutex object.
void osReleaseMutex(OsMutex *mutex)
Release ownership of the specified mutex object.
OsMutex efm32gg11CryptoMutex
#define EcCurve
Definition: ec.h:346
__weak_func void ecScalarMul(uint32_t *rl, uint32_t *rh, const uint32_t *a, const uint32_t *b, uint_t n)
Multiplication of two integers.
Definition: ec_misc.c:766
unsigned int uint_t
Definition: compiler_port.h:57
ECC (Elliptic Curve Cryptography)
#define EC_MAX_MODULUS_SIZE
Definition: ec.h:284
Debugging facilities.
void ecFieldMulMod(const EcCurve *curve, uint32_t *r, const uint32_t *a, const uint32_t *b)
Modular multiplication.