1 /*
2 * Copyright (c) 2020-2022, Intel Corporation. All rights reserved.
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7 #include <arch_helpers.h>
8 #include <lib/mmio.h>
9
10 #include "socfpga_fcs.h"
11 #include "socfpga_mailbox.h"
12 #include "socfpga_sip_svc.h"
13
14 /* FCS static variables */
15 static fcs_crypto_service_aes_data fcs_aes_init_payload;
16 static fcs_crypto_service_data fcs_sha_get_digest_param;
17 static fcs_crypto_service_data fcs_sha_mac_verify_param;
18 static fcs_crypto_service_data fcs_ecdsa_hash_sign_param;
19 static fcs_crypto_service_data fcs_ecdsa_hash_sig_verify_param;
20 static fcs_crypto_service_data fcs_sha2_data_sign_param;
21 static fcs_crypto_service_data fcs_sha2_data_sig_verify_param;
22 static fcs_crypto_service_data fcs_ecdsa_get_pubkey_param;
23 static fcs_crypto_service_data fcs_ecdh_request_param;
24
is_size_4_bytes_aligned(uint32_t size)25 bool is_size_4_bytes_aligned(uint32_t size)
26 {
27 if ((size % MBOX_WORD_BYTE) != 0U) {
28 return false;
29 } else {
30 return true;
31 }
32 }
33
is_8_bytes_aligned(uint32_t data)34 static bool is_8_bytes_aligned(uint32_t data)
35 {
36 if ((data % (MBOX_WORD_BYTE * 2U)) != 0U) {
37 return false;
38 } else {
39 return true;
40 }
41 }
42
is_32_bytes_aligned(uint32_t data)43 static bool is_32_bytes_aligned(uint32_t data)
44 {
45 if ((data % (8U * MBOX_WORD_BYTE)) != 0U) {
46 return false;
47 } else {
48 return true;
49 }
50 }
51
intel_fcs_crypto_service_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,fcs_crypto_service_data * data_addr,uint32_t * mbox_error)52 static int intel_fcs_crypto_service_init(uint32_t session_id,
53 uint32_t context_id, uint32_t key_id,
54 uint32_t param_size, uint64_t param_data,
55 fcs_crypto_service_data *data_addr,
56 uint32_t *mbox_error)
57 {
58 if (mbox_error == NULL) {
59 return INTEL_SIP_SMC_STATUS_REJECTED;
60 }
61
62 if (param_size != 4) {
63 return INTEL_SIP_SMC_STATUS_REJECTED;
64 }
65
66 memset(data_addr, 0, sizeof(fcs_crypto_service_data));
67
68 data_addr->session_id = session_id;
69 data_addr->context_id = context_id;
70 data_addr->key_id = key_id;
71 data_addr->crypto_param_size = param_size;
72 data_addr->crypto_param = param_data;
73
74 data_addr->is_updated = 0;
75
76 *mbox_error = 0;
77
78 return INTEL_SIP_SMC_STATUS_OK;
79 }
80
intel_fcs_random_number_gen(uint64_t addr,uint64_t * ret_size,uint32_t * mbox_error)81 uint32_t intel_fcs_random_number_gen(uint64_t addr, uint64_t *ret_size,
82 uint32_t *mbox_error)
83 {
84 int status;
85 unsigned int i;
86 unsigned int resp_len = FCS_RANDOM_WORD_SIZE;
87 uint32_t random_data[FCS_RANDOM_WORD_SIZE] = {0U};
88
89 if (!is_address_in_ddr_range(addr, FCS_RANDOM_BYTE_SIZE)) {
90 return INTEL_SIP_SMC_STATUS_REJECTED;
91 }
92
93 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_RANDOM_GEN, NULL, 0U,
94 CMD_CASUAL, random_data, &resp_len);
95
96 if (status < 0) {
97 *mbox_error = -status;
98 return INTEL_SIP_SMC_STATUS_ERROR;
99 }
100
101 if (resp_len != FCS_RANDOM_WORD_SIZE) {
102 *mbox_error = GENERIC_RESPONSE_ERROR;
103 return INTEL_SIP_SMC_STATUS_ERROR;
104 }
105
106 *ret_size = FCS_RANDOM_BYTE_SIZE;
107
108 for (i = 0U; i < FCS_RANDOM_WORD_SIZE; i++) {
109 mmio_write_32(addr, random_data[i]);
110 addr += MBOX_WORD_BYTE;
111 }
112
113 flush_dcache_range(addr - *ret_size, *ret_size);
114
115 return INTEL_SIP_SMC_STATUS_OK;
116 }
117
intel_fcs_random_number_gen_ext(uint32_t session_id,uint32_t context_id,uint32_t size,uint32_t * send_id)118 int intel_fcs_random_number_gen_ext(uint32_t session_id, uint32_t context_id,
119 uint32_t size, uint32_t *send_id)
120 {
121 int status;
122 uint32_t payload_size;
123 uint32_t crypto_header;
124
125 if (size > (FCS_RANDOM_EXT_MAX_WORD_SIZE *
126 MBOX_WORD_BYTE) || size == 0U) {
127 return INTEL_SIP_SMC_STATUS_REJECTED;
128 }
129
130 if (!is_size_4_bytes_aligned(size)) {
131 return INTEL_SIP_SMC_STATUS_REJECTED;
132 }
133
134 crypto_header = (FCS_CS_FIELD_FLAG_INIT | FCS_CS_FIELD_FLAG_FINALIZE) <<
135 FCS_CS_FIELD_FLAG_OFFSET;
136
137 fcs_rng_payload payload = {
138 session_id,
139 context_id,
140 crypto_header,
141 size
142 };
143
144 payload_size = sizeof(payload) / MBOX_WORD_BYTE;
145
146 status = mailbox_send_cmd_async(send_id, MBOX_FCS_RANDOM_GEN,
147 (uint32_t *) &payload, payload_size,
148 CMD_INDIRECT);
149
150 if (status < 0) {
151 return INTEL_SIP_SMC_STATUS_ERROR;
152 }
153
154 return INTEL_SIP_SMC_STATUS_OK;
155 }
156
intel_fcs_send_cert(uint64_t addr,uint64_t size,uint32_t * send_id)157 uint32_t intel_fcs_send_cert(uint64_t addr, uint64_t size,
158 uint32_t *send_id)
159 {
160 int status;
161
162 if (!is_address_in_ddr_range(addr, size)) {
163 return INTEL_SIP_SMC_STATUS_REJECTED;
164 }
165
166 if (!is_size_4_bytes_aligned(size)) {
167 return INTEL_SIP_SMC_STATUS_REJECTED;
168 }
169
170 status = mailbox_send_cmd_async(send_id, MBOX_CMD_VAB_SRC_CERT,
171 (uint32_t *)addr, size / MBOX_WORD_BYTE,
172 CMD_DIRECT);
173
174 flush_dcache_range(addr, size);
175
176 if (status < 0) {
177 return INTEL_SIP_SMC_STATUS_ERROR;
178 }
179
180 return INTEL_SIP_SMC_STATUS_OK;
181 }
182
intel_fcs_get_provision_data(uint32_t * send_id)183 uint32_t intel_fcs_get_provision_data(uint32_t *send_id)
184 {
185 int status;
186
187 status = mailbox_send_cmd_async(send_id, MBOX_FCS_GET_PROVISION,
188 NULL, 0U, CMD_DIRECT);
189
190 if (status < 0) {
191 return INTEL_SIP_SMC_STATUS_ERROR;
192 }
193
194 return INTEL_SIP_SMC_STATUS_OK;
195 }
196
intel_fcs_cntr_set_preauth(uint8_t counter_type,int32_t counter_value,uint32_t test_bit,uint32_t * mbox_error)197 uint32_t intel_fcs_cntr_set_preauth(uint8_t counter_type, int32_t counter_value,
198 uint32_t test_bit, uint32_t *mbox_error)
199 {
200 int status;
201 uint32_t first_word;
202 uint32_t payload_size;
203
204 if ((test_bit != MBOX_TEST_BIT) &&
205 (test_bit != 0)) {
206 return INTEL_SIP_SMC_STATUS_REJECTED;
207 }
208
209 if ((counter_type < FCS_BIG_CNTR_SEL) ||
210 (counter_type > FCS_SVN_CNTR_3_SEL)) {
211 return INTEL_SIP_SMC_STATUS_REJECTED;
212 }
213
214 if ((counter_type == FCS_BIG_CNTR_SEL) &&
215 (counter_value > FCS_BIG_CNTR_VAL_MAX)) {
216 return INTEL_SIP_SMC_STATUS_REJECTED;
217 }
218
219 if ((counter_type >= FCS_SVN_CNTR_0_SEL) &&
220 (counter_type <= FCS_SVN_CNTR_3_SEL) &&
221 (counter_value > FCS_SVN_CNTR_VAL_MAX)) {
222 return INTEL_SIP_SMC_STATUS_REJECTED;
223 }
224
225 first_word = test_bit | counter_type;
226 fcs_cntr_set_preauth_payload payload = {
227 first_word,
228 counter_value
229 };
230
231 payload_size = sizeof(payload) / MBOX_WORD_BYTE;
232 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_CNTR_SET_PREAUTH,
233 (uint32_t *) &payload, payload_size,
234 CMD_CASUAL, NULL, NULL);
235
236 if (status < 0) {
237 *mbox_error = -status;
238 return INTEL_SIP_SMC_STATUS_ERROR;
239 }
240
241 return INTEL_SIP_SMC_STATUS_OK;
242 }
243
intel_fcs_encryption(uint32_t src_addr,uint32_t src_size,uint32_t dst_addr,uint32_t dst_size,uint32_t * send_id)244 uint32_t intel_fcs_encryption(uint32_t src_addr, uint32_t src_size,
245 uint32_t dst_addr, uint32_t dst_size, uint32_t *send_id)
246 {
247 int status;
248 uint32_t load_size;
249
250 fcs_encrypt_payload payload = {
251 FCS_ENCRYPTION_DATA_0,
252 src_addr,
253 src_size,
254 dst_addr,
255 dst_size };
256 load_size = sizeof(payload) / MBOX_WORD_BYTE;
257
258 if (!is_address_in_ddr_range(src_addr, src_size) ||
259 !is_address_in_ddr_range(dst_addr, dst_size)) {
260 return INTEL_SIP_SMC_STATUS_REJECTED;
261 }
262
263 if (!is_size_4_bytes_aligned(src_size)) {
264 return INTEL_SIP_SMC_STATUS_REJECTED;
265 }
266
267 status = mailbox_send_cmd_async(send_id, MBOX_FCS_ENCRYPT_REQ,
268 (uint32_t *) &payload, load_size,
269 CMD_INDIRECT);
270 inv_dcache_range(dst_addr, dst_size);
271
272 if (status < 0) {
273 return INTEL_SIP_SMC_STATUS_REJECTED;
274 }
275
276 return INTEL_SIP_SMC_STATUS_OK;
277 }
278
intel_fcs_decryption(uint32_t src_addr,uint32_t src_size,uint32_t dst_addr,uint32_t dst_size,uint32_t * send_id)279 uint32_t intel_fcs_decryption(uint32_t src_addr, uint32_t src_size,
280 uint32_t dst_addr, uint32_t dst_size, uint32_t *send_id)
281 {
282 int status;
283 uint32_t load_size;
284 uintptr_t id_offset;
285
286 id_offset = src_addr + FCS_OWNER_ID_OFFSET;
287 fcs_decrypt_payload payload = {
288 FCS_DECRYPTION_DATA_0,
289 {mmio_read_32(id_offset),
290 mmio_read_32(id_offset + MBOX_WORD_BYTE)},
291 src_addr,
292 src_size,
293 dst_addr,
294 dst_size };
295 load_size = sizeof(payload) / MBOX_WORD_BYTE;
296
297 if (!is_address_in_ddr_range(src_addr, src_size) ||
298 !is_address_in_ddr_range(dst_addr, dst_size)) {
299 return INTEL_SIP_SMC_STATUS_REJECTED;
300 }
301
302 if (!is_size_4_bytes_aligned(src_size)) {
303 return INTEL_SIP_SMC_STATUS_REJECTED;
304 }
305
306 status = mailbox_send_cmd_async(send_id, MBOX_FCS_DECRYPT_REQ,
307 (uint32_t *) &payload, load_size,
308 CMD_INDIRECT);
309 inv_dcache_range(dst_addr, dst_size);
310
311 if (status < 0) {
312 return INTEL_SIP_SMC_STATUS_REJECTED;
313 }
314
315 return INTEL_SIP_SMC_STATUS_OK;
316 }
317
intel_fcs_encryption_ext(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint32_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)318 int intel_fcs_encryption_ext(uint32_t session_id, uint32_t context_id,
319 uint32_t src_addr, uint32_t src_size,
320 uint32_t dst_addr, uint32_t *dst_size, uint32_t *mbox_error)
321 {
322 int status;
323 uint32_t payload_size;
324 uint32_t resp_len = FCS_CRYPTION_RESP_WORD_SIZE;
325 uint32_t resp_data[FCS_CRYPTION_RESP_WORD_SIZE] = {0U};
326
327 if ((dst_size == NULL) || (mbox_error == NULL)) {
328 return INTEL_SIP_SMC_STATUS_REJECTED;
329 }
330
331 if (!is_address_in_ddr_range(src_addr, src_size) ||
332 !is_address_in_ddr_range(dst_addr, *dst_size)) {
333 return INTEL_SIP_SMC_STATUS_REJECTED;
334 }
335
336 if (!is_size_4_bytes_aligned(src_size)) {
337 return INTEL_SIP_SMC_STATUS_REJECTED;
338 }
339
340 fcs_encrypt_ext_payload payload = {
341 session_id,
342 context_id,
343 FCS_CRYPTION_CRYPTO_HEADER,
344 src_addr,
345 src_size,
346 dst_addr,
347 *dst_size
348 };
349
350 payload_size = sizeof(payload) / MBOX_WORD_BYTE;
351
352 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_ENCRYPT_REQ,
353 (uint32_t *) &payload, payload_size,
354 CMD_CASUAL, resp_data, &resp_len);
355
356 if (status < 0) {
357 *mbox_error = -status;
358 return INTEL_SIP_SMC_STATUS_ERROR;
359 }
360
361 if (resp_len != FCS_CRYPTION_RESP_WORD_SIZE) {
362 *mbox_error = MBOX_RET_ERROR;
363 return INTEL_SIP_SMC_STATUS_ERROR;
364 }
365
366 *dst_size = resp_data[FCS_CRYPTION_RESP_SIZE_OFFSET];
367 inv_dcache_range(dst_addr, *dst_size);
368
369 return INTEL_SIP_SMC_STATUS_OK;
370 }
371
intel_fcs_decryption_ext(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint32_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)372 int intel_fcs_decryption_ext(uint32_t session_id, uint32_t context_id,
373 uint32_t src_addr, uint32_t src_size,
374 uint32_t dst_addr, uint32_t *dst_size, uint32_t *mbox_error)
375 {
376 int status;
377 uintptr_t id_offset;
378 uint32_t payload_size;
379 uint32_t resp_len = FCS_CRYPTION_RESP_WORD_SIZE;
380 uint32_t resp_data[FCS_CRYPTION_RESP_WORD_SIZE] = {0U};
381
382 if ((dst_size == NULL) || (mbox_error == NULL)) {
383 return INTEL_SIP_SMC_STATUS_REJECTED;
384 }
385
386 if (!is_address_in_ddr_range(src_addr, src_size) ||
387 !is_address_in_ddr_range(dst_addr, *dst_size)) {
388 return INTEL_SIP_SMC_STATUS_REJECTED;
389 }
390
391 if (!is_size_4_bytes_aligned(src_size)) {
392 return INTEL_SIP_SMC_STATUS_REJECTED;
393 }
394
395 id_offset = src_addr + FCS_OWNER_ID_OFFSET;
396 fcs_decrypt_ext_payload payload = {
397 session_id,
398 context_id,
399 FCS_CRYPTION_CRYPTO_HEADER,
400 {mmio_read_32(id_offset),
401 mmio_read_32(id_offset + MBOX_WORD_BYTE)},
402 src_addr,
403 src_size,
404 dst_addr,
405 *dst_size
406 };
407
408 payload_size = sizeof(payload) / MBOX_WORD_BYTE;
409
410 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_DECRYPT_REQ,
411 (uint32_t *) &payload, payload_size,
412 CMD_CASUAL, resp_data, &resp_len);
413
414 if (status < 0) {
415 *mbox_error = -status;
416 return INTEL_SIP_SMC_STATUS_ERROR;
417 }
418
419 if (resp_len != FCS_CRYPTION_RESP_WORD_SIZE) {
420 *mbox_error = MBOX_RET_ERROR;
421 return INTEL_SIP_SMC_STATUS_ERROR;
422 }
423
424 *dst_size = resp_data[FCS_CRYPTION_RESP_SIZE_OFFSET];
425 inv_dcache_range(dst_addr, *dst_size);
426
427 return INTEL_SIP_SMC_STATUS_OK;
428 }
429
intel_fcs_sigma_teardown(uint32_t session_id,uint32_t * mbox_error)430 int intel_fcs_sigma_teardown(uint32_t session_id, uint32_t *mbox_error)
431 {
432 int status;
433
434 if ((session_id != PSGSIGMA_SESSION_ID_ONE) &&
435 (session_id != PSGSIGMA_UNKNOWN_SESSION)) {
436 return INTEL_SIP_SMC_STATUS_REJECTED;
437 }
438
439 psgsigma_teardown_msg message = {
440 RESERVED_AS_ZERO,
441 PSGSIGMA_TEARDOWN_MAGIC,
442 session_id
443 };
444
445 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_PSG_SIGMA_TEARDOWN,
446 (uint32_t *) &message, sizeof(message) / MBOX_WORD_BYTE,
447 CMD_CASUAL, NULL, NULL);
448
449 if (status < 0) {
450 *mbox_error = -status;
451 return INTEL_SIP_SMC_STATUS_ERROR;
452 }
453
454 return INTEL_SIP_SMC_STATUS_OK;
455 }
456
intel_fcs_chip_id(uint32_t * id_low,uint32_t * id_high,uint32_t * mbox_error)457 int intel_fcs_chip_id(uint32_t *id_low, uint32_t *id_high, uint32_t *mbox_error)
458 {
459 int status;
460 uint32_t load_size;
461 uint32_t chip_id[2];
462
463 load_size = sizeof(chip_id) / MBOX_WORD_BYTE;
464
465 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_CMD_GET_CHIPID, NULL,
466 0U, CMD_CASUAL, (uint32_t *) chip_id, &load_size);
467
468 if (status < 0) {
469 *mbox_error = -status;
470 return INTEL_SIP_SMC_STATUS_ERROR;
471 }
472
473 *id_low = chip_id[0];
474 *id_high = chip_id[1];
475
476 return INTEL_SIP_SMC_STATUS_OK;
477 }
478
intel_fcs_attestation_subkey(uint64_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)479 int intel_fcs_attestation_subkey(uint64_t src_addr, uint32_t src_size,
480 uint64_t dst_addr, uint32_t *dst_size, uint32_t *mbox_error)
481 {
482 int status;
483 uint32_t send_size = src_size / MBOX_WORD_BYTE;
484 uint32_t ret_size = *dst_size / MBOX_WORD_BYTE;
485
486
487 if (!is_address_in_ddr_range(src_addr, src_size) ||
488 !is_address_in_ddr_range(dst_addr, *dst_size)) {
489 return INTEL_SIP_SMC_STATUS_REJECTED;
490 }
491
492 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_ATTESTATION_SUBKEY,
493 (uint32_t *) src_addr, send_size, CMD_CASUAL,
494 (uint32_t *) dst_addr, &ret_size);
495
496 if (status < 0) {
497 *mbox_error = -status;
498 return INTEL_SIP_SMC_STATUS_ERROR;
499 }
500
501 *dst_size = ret_size * MBOX_WORD_BYTE;
502 flush_dcache_range(dst_addr, *dst_size);
503
504 return INTEL_SIP_SMC_STATUS_OK;
505 }
506
intel_fcs_get_measurement(uint64_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)507 int intel_fcs_get_measurement(uint64_t src_addr, uint32_t src_size,
508 uint64_t dst_addr, uint32_t *dst_size, uint32_t *mbox_error)
509 {
510 int status;
511 uint32_t send_size = src_size / MBOX_WORD_BYTE;
512 uint32_t ret_size = *dst_size / MBOX_WORD_BYTE;
513
514 if (!is_address_in_ddr_range(src_addr, src_size) ||
515 !is_address_in_ddr_range(dst_addr, *dst_size)) {
516 return INTEL_SIP_SMC_STATUS_REJECTED;
517 }
518
519 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_GET_MEASUREMENT,
520 (uint32_t *) src_addr, send_size, CMD_CASUAL,
521 (uint32_t *) dst_addr, &ret_size);
522
523 if (status < 0) {
524 *mbox_error = -status;
525 return INTEL_SIP_SMC_STATUS_ERROR;
526 }
527
528 *dst_size = ret_size * MBOX_WORD_BYTE;
529 flush_dcache_range(dst_addr, *dst_size);
530
531 return INTEL_SIP_SMC_STATUS_OK;
532 }
533
intel_fcs_get_rom_patch_sha384(uint64_t addr,uint64_t * ret_size,uint32_t * mbox_error)534 uint32_t intel_fcs_get_rom_patch_sha384(uint64_t addr, uint64_t *ret_size,
535 uint32_t *mbox_error)
536 {
537 int status;
538 unsigned int resp_len = FCS_SHA384_WORD_SIZE;
539
540 if (!is_address_in_ddr_range(addr, FCS_SHA384_BYTE_SIZE)) {
541 return INTEL_SIP_SMC_STATUS_REJECTED;
542 }
543
544 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_GET_ROM_PATCH_SHA384, NULL, 0U,
545 CMD_CASUAL, (uint32_t *) addr, &resp_len);
546
547 if (status < 0) {
548 *mbox_error = -status;
549 return INTEL_SIP_SMC_STATUS_ERROR;
550 }
551
552 if (resp_len != FCS_SHA384_WORD_SIZE) {
553 *mbox_error = GENERIC_RESPONSE_ERROR;
554 return INTEL_SIP_SMC_STATUS_ERROR;
555 }
556
557 *ret_size = FCS_SHA384_BYTE_SIZE;
558
559 flush_dcache_range(addr, *ret_size);
560
561 return INTEL_SIP_SMC_STATUS_OK;
562 }
563
intel_fcs_get_attestation_cert(uint32_t cert_request,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)564 int intel_fcs_get_attestation_cert(uint32_t cert_request, uint64_t dst_addr,
565 uint32_t *dst_size, uint32_t *mbox_error)
566 {
567 int status;
568 uint32_t ret_size = *dst_size / MBOX_WORD_BYTE;
569
570 if (mbox_error == NULL) {
571 return INTEL_SIP_SMC_STATUS_REJECTED;
572 }
573
574 if (cert_request < FCS_ATTEST_FIRMWARE_CERT ||
575 cert_request > FCS_ATTEST_CERT_MAX_REQ_PARAM) {
576 return INTEL_SIP_SMC_STATUS_REJECTED;
577 }
578
579 if (!is_address_in_ddr_range(dst_addr, *dst_size)) {
580 return INTEL_SIP_SMC_STATUS_REJECTED;
581 }
582
583 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_GET_ATTESTATION_CERT,
584 (uint32_t *) &cert_request, 1U, CMD_CASUAL,
585 (uint32_t *) dst_addr, &ret_size);
586
587 if (status < 0) {
588 *mbox_error = -status;
589 return INTEL_SIP_SMC_STATUS_ERROR;
590 }
591
592 *dst_size = ret_size * MBOX_WORD_BYTE;
593 flush_dcache_range(dst_addr, *dst_size);
594
595 return INTEL_SIP_SMC_STATUS_OK;
596 }
597
intel_fcs_create_cert_on_reload(uint32_t cert_request,uint32_t * mbox_error)598 int intel_fcs_create_cert_on_reload(uint32_t cert_request,
599 uint32_t *mbox_error)
600 {
601 int status;
602
603 if (mbox_error == NULL) {
604 return INTEL_SIP_SMC_STATUS_REJECTED;
605 }
606
607 if (cert_request < FCS_ATTEST_FIRMWARE_CERT ||
608 cert_request > FCS_ATTEST_CERT_MAX_REQ_PARAM) {
609 return INTEL_SIP_SMC_STATUS_REJECTED;
610 }
611
612 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_CREATE_CERT_ON_RELOAD,
613 (uint32_t *) &cert_request, 1U, CMD_CASUAL,
614 NULL, NULL);
615
616 if (status < 0) {
617 *mbox_error = -status;
618 return INTEL_SIP_SMC_STATUS_ERROR;
619 }
620
621 return INTEL_SIP_SMC_STATUS_OK;
622 }
623
intel_fcs_open_crypto_service_session(uint32_t * session_id,uint32_t * mbox_error)624 int intel_fcs_open_crypto_service_session(uint32_t *session_id,
625 uint32_t *mbox_error)
626 {
627 int status;
628 uint32_t resp_len = 1U;
629
630 if ((session_id == NULL) || (mbox_error == NULL)) {
631 return INTEL_SIP_SMC_STATUS_REJECTED;
632 }
633
634 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_OPEN_CS_SESSION,
635 NULL, 0U, CMD_CASUAL, session_id, &resp_len);
636
637 if (status < 0) {
638 *mbox_error = -status;
639 return INTEL_SIP_SMC_STATUS_ERROR;
640 }
641
642 return INTEL_SIP_SMC_STATUS_OK;
643 }
644
intel_fcs_close_crypto_service_session(uint32_t session_id,uint32_t * mbox_error)645 int intel_fcs_close_crypto_service_session(uint32_t session_id,
646 uint32_t *mbox_error)
647 {
648 int status;
649
650 if (mbox_error == NULL) {
651 return INTEL_SIP_SMC_STATUS_REJECTED;
652 }
653
654 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_CLOSE_CS_SESSION,
655 &session_id, 1U, CMD_CASUAL, NULL, NULL);
656
657 if (status < 0) {
658 *mbox_error = -status;
659 return INTEL_SIP_SMC_STATUS_ERROR;
660 }
661
662 return INTEL_SIP_SMC_STATUS_OK;
663 }
664
intel_fcs_import_crypto_service_key(uint64_t src_addr,uint32_t src_size,uint32_t * send_id)665 int intel_fcs_import_crypto_service_key(uint64_t src_addr, uint32_t src_size,
666 uint32_t *send_id)
667 {
668 int status;
669
670 if (src_size > (FCS_CS_KEY_OBJ_MAX_WORD_SIZE *
671 MBOX_WORD_BYTE)) {
672 return INTEL_SIP_SMC_STATUS_REJECTED;
673 }
674
675 if (!is_address_in_ddr_range(src_addr, src_size)) {
676 return INTEL_SIP_SMC_STATUS_REJECTED;
677 }
678
679 status = mailbox_send_cmd_async(send_id, MBOX_FCS_IMPORT_CS_KEY,
680 (uint32_t *)src_addr, src_size / MBOX_WORD_BYTE,
681 CMD_INDIRECT);
682
683 if (status < 0) {
684 return INTEL_SIP_SMC_STATUS_ERROR;
685 }
686
687 return INTEL_SIP_SMC_STATUS_OK;
688 }
689
intel_fcs_export_crypto_service_key(uint32_t session_id,uint32_t key_id,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)690 int intel_fcs_export_crypto_service_key(uint32_t session_id, uint32_t key_id,
691 uint64_t dst_addr, uint32_t *dst_size,
692 uint32_t *mbox_error)
693 {
694 int status;
695 uint32_t i;
696 uint32_t payload_size;
697 uint32_t resp_len = FCS_CS_KEY_OBJ_MAX_WORD_SIZE;
698 uint32_t resp_data[FCS_CS_KEY_OBJ_MAX_WORD_SIZE] = {0U};
699 uint32_t op_status = 0U;
700
701 if ((dst_size == NULL) || (mbox_error == NULL)) {
702 return INTEL_SIP_SMC_STATUS_REJECTED;
703 }
704
705 if (!is_address_in_ddr_range(dst_addr, *dst_size)) {
706 return INTEL_SIP_SMC_STATUS_REJECTED;
707 }
708
709 fcs_cs_key_payload payload = {
710 session_id,
711 RESERVED_AS_ZERO,
712 RESERVED_AS_ZERO,
713 key_id
714 };
715
716 payload_size = sizeof(payload) / MBOX_WORD_BYTE;
717
718 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_EXPORT_CS_KEY,
719 (uint32_t *) &payload, payload_size,
720 CMD_CASUAL, resp_data, &resp_len);
721
722 if (resp_len > 0) {
723 op_status = resp_data[0] & FCS_CS_KEY_RESP_STATUS_MASK;
724 }
725
726 if (status < 0) {
727 *mbox_error = (-status) | (op_status << FCS_CS_KEY_RESP_STATUS_OFFSET);
728 return INTEL_SIP_SMC_STATUS_ERROR;
729 }
730
731 if (resp_len > 1) {
732
733 /* Export key object is start at second response data */
734 *dst_size = (resp_len - 1) * MBOX_WORD_BYTE;
735
736 for (i = 1U; i < resp_len; i++) {
737 mmio_write_32(dst_addr, resp_data[i]);
738 dst_addr += MBOX_WORD_BYTE;
739 }
740
741 flush_dcache_range(dst_addr - *dst_size, *dst_size);
742
743 } else {
744
745 /* Unexpected response, missing key object in response */
746 *mbox_error = MBOX_RET_ERROR;
747 return INTEL_SIP_SMC_STATUS_ERROR;
748 }
749
750 return INTEL_SIP_SMC_STATUS_OK;
751 }
752
intel_fcs_remove_crypto_service_key(uint32_t session_id,uint32_t key_id,uint32_t * mbox_error)753 int intel_fcs_remove_crypto_service_key(uint32_t session_id, uint32_t key_id,
754 uint32_t *mbox_error)
755 {
756 int status;
757 uint32_t payload_size;
758 uint32_t resp_len = 1U;
759 uint32_t resp_data = 0U;
760 uint32_t op_status = 0U;
761
762 if (mbox_error == NULL) {
763 return INTEL_SIP_SMC_STATUS_REJECTED;
764 }
765
766 fcs_cs_key_payload payload = {
767 session_id,
768 RESERVED_AS_ZERO,
769 RESERVED_AS_ZERO,
770 key_id
771 };
772
773 payload_size = sizeof(payload) / MBOX_WORD_BYTE;
774
775 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_REMOVE_CS_KEY,
776 (uint32_t *) &payload, payload_size,
777 CMD_CASUAL, &resp_data, &resp_len);
778
779 if (resp_len > 0) {
780 op_status = resp_data & FCS_CS_KEY_RESP_STATUS_MASK;
781 }
782
783 if (status < 0) {
784 *mbox_error = (-status) | (op_status << FCS_CS_KEY_RESP_STATUS_OFFSET);
785 return INTEL_SIP_SMC_STATUS_ERROR;
786 }
787
788 return INTEL_SIP_SMC_STATUS_OK;
789 }
790
intel_fcs_get_crypto_service_key_info(uint32_t session_id,uint32_t key_id,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)791 int intel_fcs_get_crypto_service_key_info(uint32_t session_id, uint32_t key_id,
792 uint64_t dst_addr, uint32_t *dst_size,
793 uint32_t *mbox_error)
794 {
795 int status;
796 uint32_t payload_size;
797 uint32_t resp_len = FCS_CS_KEY_INFO_MAX_WORD_SIZE;
798 uint32_t op_status = 0U;
799
800 if ((dst_size == NULL) || (mbox_error == NULL)) {
801 return INTEL_SIP_SMC_STATUS_REJECTED;
802 }
803
804 if (!is_address_in_ddr_range(dst_addr, *dst_size)) {
805 return INTEL_SIP_SMC_STATUS_REJECTED;
806 }
807
808 fcs_cs_key_payload payload = {
809 session_id,
810 RESERVED_AS_ZERO,
811 RESERVED_AS_ZERO,
812 key_id
813 };
814
815 payload_size = sizeof(payload) / MBOX_WORD_BYTE;
816
817 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_GET_CS_KEY_INFO,
818 (uint32_t *) &payload, payload_size,
819 CMD_CASUAL, (uint32_t *) dst_addr, &resp_len);
820
821 if (resp_len > 0) {
822 op_status = mmio_read_32(dst_addr) &
823 FCS_CS_KEY_RESP_STATUS_MASK;
824 }
825
826 if (status < 0) {
827 *mbox_error = (-status) | (op_status << FCS_CS_KEY_RESP_STATUS_OFFSET);
828 return INTEL_SIP_SMC_STATUS_ERROR;
829 }
830
831 *dst_size = resp_len * MBOX_WORD_BYTE;
832 flush_dcache_range(dst_addr, *dst_size);
833
834 return INTEL_SIP_SMC_STATUS_OK;
835 }
836
intel_fcs_get_digest_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)837 int intel_fcs_get_digest_init(uint32_t session_id, uint32_t context_id,
838 uint32_t key_id, uint32_t param_size,
839 uint64_t param_data, uint32_t *mbox_error)
840 {
841 return intel_fcs_crypto_service_init(session_id, context_id,
842 key_id, param_size, param_data,
843 (void *) &fcs_sha_get_digest_param,
844 mbox_error);
845 }
846
intel_fcs_get_digest_update_finalize(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint8_t is_finalised,uint32_t * mbox_error)847 int intel_fcs_get_digest_update_finalize(uint32_t session_id,
848 uint32_t context_id, uint32_t src_addr,
849 uint32_t src_size, uint64_t dst_addr,
850 uint32_t *dst_size, uint8_t is_finalised,
851 uint32_t *mbox_error)
852 {
853 int status;
854 uint32_t i;
855 uint32_t flag;
856 uint32_t crypto_header;
857 uint32_t resp_len;
858 uint32_t payload[FCS_GET_DIGEST_CMD_MAX_WORD_SIZE] = {0U};
859
860 if (dst_size == NULL || mbox_error == NULL) {
861 return INTEL_SIP_SMC_STATUS_REJECTED;
862 }
863
864 if (fcs_sha_get_digest_param.session_id != session_id ||
865 fcs_sha_get_digest_param.context_id != context_id) {
866 return INTEL_SIP_SMC_STATUS_REJECTED;
867 }
868
869 /* Source data must be 8 bytes aligned */
870 if (!is_8_bytes_aligned(src_size)) {
871 return INTEL_SIP_SMC_STATUS_REJECTED;
872 }
873
874 if (!is_address_in_ddr_range(src_addr, src_size) ||
875 !is_address_in_ddr_range(dst_addr, *dst_size)) {
876 return INTEL_SIP_SMC_STATUS_REJECTED;
877 }
878
879 resp_len = *dst_size / MBOX_WORD_BYTE;
880
881 /* Prepare crypto header */
882 flag = 0;
883
884 if (fcs_sha_get_digest_param.is_updated) {
885 fcs_sha_get_digest_param.crypto_param_size = 0;
886 } else {
887 flag |= FCS_CS_FIELD_FLAG_INIT;
888 }
889
890 if (is_finalised != 0U) {
891 flag |= FCS_CS_FIELD_FLAG_FINALIZE;
892 } else {
893 flag |= FCS_CS_FIELD_FLAG_UPDATE;
894 fcs_sha_get_digest_param.is_updated = 1;
895 }
896
897 crypto_header = ((flag << FCS_CS_FIELD_FLAG_OFFSET) |
898 (fcs_sha_get_digest_param.crypto_param_size &
899 FCS_CS_FIELD_SIZE_MASK));
900
901 /* Prepare command payload */
902 i = 0;
903 payload[i] = fcs_sha_get_digest_param.session_id;
904 i++;
905 payload[i] = fcs_sha_get_digest_param.context_id;
906 i++;
907 payload[i] = crypto_header;
908 i++;
909
910 if ((crypto_header >> FCS_CS_FIELD_FLAG_OFFSET) &
911 FCS_CS_FIELD_FLAG_INIT) {
912 payload[i] = fcs_sha_get_digest_param.key_id;
913 i++;
914 /* Crypto parameters */
915 payload[i] = fcs_sha_get_digest_param.crypto_param
916 & INTEL_SIP_SMC_FCS_SHA_MODE_MASK;
917 payload[i] |= ((fcs_sha_get_digest_param.crypto_param
918 >> INTEL_SIP_SMC_FCS_DIGEST_SIZE_OFFSET)
919 & INTEL_SIP_SMC_FCS_DIGEST_SIZE_MASK)
920 << FCS_SHA_HMAC_CRYPTO_PARAM_SIZE_OFFSET;
921 i++;
922 }
923 /* Data source address and size */
924 payload[i] = src_addr;
925 i++;
926 payload[i] = src_size;
927 i++;
928
929 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_GET_DIGEST_REQ,
930 payload, i, CMD_CASUAL,
931 (uint32_t *) dst_addr, &resp_len);
932
933 if (is_finalised != 0U) {
934 memset((void *)&fcs_sha_get_digest_param, 0,
935 sizeof(fcs_crypto_service_data));
936 }
937
938 if (status < 0) {
939 *mbox_error = -status;
940 return INTEL_SIP_SMC_STATUS_ERROR;
941 }
942
943 *dst_size = resp_len * MBOX_WORD_BYTE;
944 flush_dcache_range(dst_addr, *dst_size);
945
946 return INTEL_SIP_SMC_STATUS_OK;
947 }
948
intel_fcs_mac_verify_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)949 int intel_fcs_mac_verify_init(uint32_t session_id, uint32_t context_id,
950 uint32_t key_id, uint32_t param_size,
951 uint64_t param_data, uint32_t *mbox_error)
952 {
953 return intel_fcs_crypto_service_init(session_id, context_id,
954 key_id, param_size, param_data,
955 (void *) &fcs_sha_mac_verify_param,
956 mbox_error);
957 }
958
intel_fcs_mac_verify_update_finalize(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint32_t data_size,uint8_t is_finalised,uint32_t * mbox_error)959 int intel_fcs_mac_verify_update_finalize(uint32_t session_id,
960 uint32_t context_id, uint32_t src_addr,
961 uint32_t src_size, uint64_t dst_addr,
962 uint32_t *dst_size, uint32_t data_size,
963 uint8_t is_finalised, uint32_t *mbox_error)
964 {
965 int status;
966 uint32_t i;
967 uint32_t flag;
968 uint32_t crypto_header;
969 uint32_t resp_len;
970 uint32_t payload[FCS_MAC_VERIFY_CMD_MAX_WORD_SIZE] = {0U};
971 uintptr_t mac_offset;
972
973 if (dst_size == NULL || mbox_error == NULL) {
974 return INTEL_SIP_SMC_STATUS_REJECTED;
975 }
976
977 if (fcs_sha_mac_verify_param.session_id != session_id ||
978 fcs_sha_mac_verify_param.context_id != context_id) {
979 return INTEL_SIP_SMC_STATUS_REJECTED;
980 }
981
982 if (data_size > src_size) {
983 return INTEL_SIP_SMC_STATUS_REJECTED;
984 }
985
986 if (!is_size_4_bytes_aligned(src_size) ||
987 !is_8_bytes_aligned(data_size)) {
988 return INTEL_SIP_SMC_STATUS_REJECTED;
989 }
990
991 if (!is_address_in_ddr_range(src_addr, src_size) ||
992 !is_address_in_ddr_range(dst_addr, *dst_size)) {
993 return INTEL_SIP_SMC_STATUS_REJECTED;
994 }
995
996 resp_len = *dst_size / MBOX_WORD_BYTE;
997
998 /* Prepare crypto header */
999 flag = 0;
1000
1001 if (fcs_sha_mac_verify_param.is_updated) {
1002 fcs_sha_mac_verify_param.crypto_param_size = 0;
1003 } else {
1004 flag |= FCS_CS_FIELD_FLAG_INIT;
1005 }
1006
1007 if (is_finalised) {
1008 flag |= FCS_CS_FIELD_FLAG_FINALIZE;
1009 } else {
1010 flag |= FCS_CS_FIELD_FLAG_UPDATE;
1011 fcs_sha_mac_verify_param.is_updated = 1;
1012 }
1013
1014 crypto_header = ((flag << FCS_CS_FIELD_FLAG_OFFSET) |
1015 (fcs_sha_mac_verify_param.crypto_param_size &
1016 FCS_CS_FIELD_SIZE_MASK));
1017
1018 /* Prepare command payload */
1019 i = 0;
1020 payload[i] = fcs_sha_mac_verify_param.session_id;
1021 i++;
1022 payload[i] = fcs_sha_mac_verify_param.context_id;
1023 i++;
1024 payload[i] = crypto_header;
1025 i++;
1026
1027 if ((crypto_header >> FCS_CS_FIELD_FLAG_OFFSET) &
1028 FCS_CS_FIELD_FLAG_INIT) {
1029 payload[i] = fcs_sha_mac_verify_param.key_id;
1030 i++;
1031 /* Crypto parameters */
1032 payload[i] = ((fcs_sha_mac_verify_param.crypto_param
1033 >> INTEL_SIP_SMC_FCS_DIGEST_SIZE_OFFSET)
1034 & INTEL_SIP_SMC_FCS_DIGEST_SIZE_MASK)
1035 << FCS_SHA_HMAC_CRYPTO_PARAM_SIZE_OFFSET;
1036 i++;
1037 }
1038 /* Data source address and size */
1039 payload[i] = src_addr;
1040 i++;
1041 payload[i] = data_size;
1042 i++;
1043
1044 if ((crypto_header >> FCS_CS_FIELD_FLAG_OFFSET) &
1045 FCS_CS_FIELD_FLAG_FINALIZE) {
1046 /* Copy mac data to command */
1047 mac_offset = src_addr + data_size;
1048 memcpy((uint8_t *) &payload[i], (uint8_t *) mac_offset,
1049 src_size - data_size);
1050
1051 i += (src_size - data_size) / MBOX_WORD_BYTE;
1052 }
1053
1054 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_MAC_VERIFY_REQ,
1055 payload, i, CMD_CASUAL,
1056 (uint32_t *) dst_addr, &resp_len);
1057
1058 if (is_finalised) {
1059 memset((void *)&fcs_sha_mac_verify_param, 0,
1060 sizeof(fcs_crypto_service_data));
1061 }
1062
1063 if (status < 0) {
1064 *mbox_error = -status;
1065 return INTEL_SIP_SMC_STATUS_ERROR;
1066 }
1067
1068 *dst_size = resp_len * MBOX_WORD_BYTE;
1069 flush_dcache_range(dst_addr, *dst_size);
1070
1071 return INTEL_SIP_SMC_STATUS_OK;
1072 }
1073
intel_fcs_ecdsa_hash_sign_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)1074 int intel_fcs_ecdsa_hash_sign_init(uint32_t session_id, uint32_t context_id,
1075 uint32_t key_id, uint32_t param_size,
1076 uint64_t param_data, uint32_t *mbox_error)
1077 {
1078 return intel_fcs_crypto_service_init(session_id, context_id,
1079 key_id, param_size, param_data,
1080 (void *) &fcs_ecdsa_hash_sign_param,
1081 mbox_error);
1082 }
1083
intel_fcs_ecdsa_hash_sign_finalize(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)1084 int intel_fcs_ecdsa_hash_sign_finalize(uint32_t session_id, uint32_t context_id,
1085 uint32_t src_addr, uint32_t src_size,
1086 uint64_t dst_addr, uint32_t *dst_size,
1087 uint32_t *mbox_error)
1088 {
1089 int status;
1090 uint32_t i;
1091 uint32_t payload[FCS_ECDSA_HASH_SIGN_CMD_MAX_WORD_SIZE] = {0U};
1092 uint32_t resp_len;
1093 uintptr_t hash_data_addr;
1094
1095 if ((dst_size == NULL) || (mbox_error == NULL)) {
1096 return INTEL_SIP_SMC_STATUS_REJECTED;
1097 }
1098
1099 if (fcs_ecdsa_hash_sign_param.session_id != session_id ||
1100 fcs_ecdsa_hash_sign_param.context_id != context_id) {
1101 return INTEL_SIP_SMC_STATUS_REJECTED;
1102 }
1103
1104 if (!is_address_in_ddr_range(src_addr, src_size) ||
1105 !is_address_in_ddr_range(dst_addr, *dst_size)) {
1106 return INTEL_SIP_SMC_STATUS_REJECTED;
1107 }
1108
1109 resp_len = *dst_size / MBOX_WORD_BYTE;
1110
1111 /* Prepare command payload */
1112 /* Crypto header */
1113 i = 0;
1114 payload[i] = fcs_ecdsa_hash_sign_param.session_id;
1115 i++;
1116 payload[i] = fcs_ecdsa_hash_sign_param.context_id;
1117
1118 i++;
1119 payload[i] = fcs_ecdsa_hash_sign_param.crypto_param_size
1120 & FCS_CS_FIELD_SIZE_MASK;
1121 payload[i] |= (FCS_CS_FIELD_FLAG_INIT | FCS_CS_FIELD_FLAG_UPDATE
1122 | FCS_CS_FIELD_FLAG_FINALIZE)
1123 << FCS_CS_FIELD_FLAG_OFFSET;
1124 i++;
1125 payload[i] = fcs_ecdsa_hash_sign_param.key_id;
1126
1127 /* Crypto parameters */
1128 i++;
1129 payload[i] = fcs_ecdsa_hash_sign_param.crypto_param
1130 & INTEL_SIP_SMC_FCS_ECC_ALGO_MASK;
1131
1132 /* Hash Data */
1133 i++;
1134 hash_data_addr = src_addr;
1135 memcpy((uint8_t *) &payload[i], (uint8_t *) hash_data_addr,
1136 src_size);
1137
1138 i += src_size / MBOX_WORD_BYTE;
1139
1140 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_ECDSA_HASH_SIGN_REQ,
1141 payload, i, CMD_CASUAL, (uint32_t *) dst_addr,
1142 &resp_len);
1143
1144 memset((void *) &fcs_ecdsa_hash_sign_param,
1145 0, sizeof(fcs_crypto_service_data));
1146
1147 if (status < 0) {
1148 *mbox_error = -status;
1149 return INTEL_SIP_SMC_STATUS_ERROR;
1150 }
1151
1152 *dst_size = resp_len * MBOX_WORD_BYTE;
1153 flush_dcache_range(dst_addr, *dst_size);
1154
1155 return INTEL_SIP_SMC_STATUS_OK;
1156 }
1157
intel_fcs_ecdsa_hash_sig_verify_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)1158 int intel_fcs_ecdsa_hash_sig_verify_init(uint32_t session_id, uint32_t context_id,
1159 uint32_t key_id, uint32_t param_size,
1160 uint64_t param_data, uint32_t *mbox_error)
1161 {
1162 return intel_fcs_crypto_service_init(session_id, context_id,
1163 key_id, param_size, param_data,
1164 (void *) &fcs_ecdsa_hash_sig_verify_param,
1165 mbox_error);
1166 }
1167
intel_fcs_ecdsa_hash_sig_verify_finalize(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)1168 int intel_fcs_ecdsa_hash_sig_verify_finalize(uint32_t session_id, uint32_t context_id,
1169 uint32_t src_addr, uint32_t src_size,
1170 uint64_t dst_addr, uint32_t *dst_size,
1171 uint32_t *mbox_error)
1172 {
1173 int status;
1174 uint32_t i = 0;
1175 uint32_t payload[FCS_ECDSA_HASH_SIG_VERIFY_CMD_MAX_WORD_SIZE] = {0U};
1176 uint32_t resp_len;
1177 uintptr_t hash_sig_pubkey_addr;
1178
1179 if ((dst_size == NULL) || (mbox_error == NULL)) {
1180 return INTEL_SIP_SMC_STATUS_REJECTED;
1181 }
1182
1183 if (fcs_ecdsa_hash_sig_verify_param.session_id != session_id ||
1184 fcs_ecdsa_hash_sig_verify_param.context_id != context_id) {
1185 return INTEL_SIP_SMC_STATUS_REJECTED;
1186 }
1187
1188 if (!is_address_in_ddr_range(src_addr, src_size) ||
1189 !is_address_in_ddr_range(dst_addr, *dst_size)) {
1190 return INTEL_SIP_SMC_STATUS_REJECTED;
1191 }
1192
1193 resp_len = *dst_size / MBOX_WORD_BYTE;
1194
1195 /* Prepare command payload */
1196 /* Crypto header */
1197 i = 0;
1198 payload[i] = fcs_ecdsa_hash_sig_verify_param.session_id;
1199
1200 i++;
1201 payload[i] = fcs_ecdsa_hash_sig_verify_param.context_id;
1202
1203 i++;
1204 payload[i] = fcs_ecdsa_hash_sig_verify_param.crypto_param_size
1205 & FCS_CS_FIELD_SIZE_MASK;
1206 payload[i] |= (FCS_CS_FIELD_FLAG_INIT | FCS_CS_FIELD_FLAG_UPDATE
1207 | FCS_CS_FIELD_FLAG_FINALIZE)
1208 << FCS_CS_FIELD_FLAG_OFFSET;
1209
1210 i++;
1211 payload[i] = fcs_ecdsa_hash_sig_verify_param.key_id;
1212
1213 /* Crypto parameters */
1214 i++;
1215 payload[i] = fcs_ecdsa_hash_sig_verify_param.crypto_param
1216 & INTEL_SIP_SMC_FCS_ECC_ALGO_MASK;
1217
1218 /* Hash Data Word, Signature Data Word and Public Key Data word */
1219 i++;
1220 hash_sig_pubkey_addr = src_addr;
1221 memcpy((uint8_t *) &payload[i],
1222 (uint8_t *) hash_sig_pubkey_addr, src_size);
1223
1224 i += (src_size / MBOX_WORD_BYTE);
1225
1226 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_ECDSA_HASH_SIG_VERIFY,
1227 payload, i, CMD_CASUAL, (uint32_t *) dst_addr,
1228 &resp_len);
1229
1230 memset((void *)&fcs_ecdsa_hash_sig_verify_param,
1231 0, sizeof(fcs_crypto_service_data));
1232
1233 if (status < 0) {
1234 *mbox_error = -status;
1235 return INTEL_SIP_SMC_STATUS_ERROR;
1236 }
1237
1238 *dst_size = resp_len * MBOX_WORD_BYTE;
1239 flush_dcache_range(dst_addr, *dst_size);
1240
1241 return INTEL_SIP_SMC_STATUS_OK;
1242 }
1243
intel_fcs_ecdsa_sha2_data_sign_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)1244 int intel_fcs_ecdsa_sha2_data_sign_init(uint32_t session_id,
1245 uint32_t context_id, uint32_t key_id,
1246 uint32_t param_size, uint64_t param_data,
1247 uint32_t *mbox_error)
1248 {
1249 return intel_fcs_crypto_service_init(session_id, context_id,
1250 key_id, param_size, param_data,
1251 (void *) &fcs_sha2_data_sign_param,
1252 mbox_error);
1253 }
1254
intel_fcs_ecdsa_sha2_data_sign_update_finalize(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint8_t is_finalised,uint32_t * mbox_error)1255 int intel_fcs_ecdsa_sha2_data_sign_update_finalize(uint32_t session_id,
1256 uint32_t context_id, uint32_t src_addr,
1257 uint32_t src_size, uint64_t dst_addr,
1258 uint32_t *dst_size, uint8_t is_finalised,
1259 uint32_t *mbox_error)
1260 {
1261 int status;
1262 int i;
1263 uint32_t flag;
1264 uint32_t crypto_header;
1265 uint32_t payload[FCS_ECDSA_SHA2_DATA_SIGN_CMD_MAX_WORD_SIZE] = {0U};
1266 uint32_t resp_len;
1267
1268 if ((dst_size == NULL) || (mbox_error == NULL)) {
1269 return INTEL_SIP_SMC_STATUS_REJECTED;
1270 }
1271
1272 if (fcs_sha2_data_sign_param.session_id != session_id ||
1273 fcs_sha2_data_sign_param.context_id != context_id) {
1274 return INTEL_SIP_SMC_STATUS_REJECTED;
1275 }
1276
1277 /* Source data must be 8 bytes aligned */
1278 if (!is_8_bytes_aligned(src_size)) {
1279 return INTEL_SIP_SMC_STATUS_REJECTED;
1280 }
1281
1282 if (!is_address_in_ddr_range(src_addr, src_size) ||
1283 !is_address_in_ddr_range(dst_addr, *dst_size)) {
1284 return INTEL_SIP_SMC_STATUS_REJECTED;
1285 }
1286
1287 resp_len = *dst_size / MBOX_WORD_BYTE;
1288
1289 /* Prepare crypto header */
1290 flag = 0;
1291 if (fcs_sha2_data_sign_param.is_updated) {
1292 fcs_sha2_data_sign_param.crypto_param_size = 0;
1293 } else {
1294 flag |= FCS_CS_FIELD_FLAG_INIT;
1295 }
1296
1297 if (is_finalised != 0U) {
1298 flag |= FCS_CS_FIELD_FLAG_FINALIZE;
1299 } else {
1300 flag |= FCS_CS_FIELD_FLAG_UPDATE;
1301 fcs_sha2_data_sign_param.is_updated = 1;
1302 }
1303 crypto_header = (flag << FCS_CS_FIELD_FLAG_OFFSET) |
1304 fcs_sha2_data_sign_param.crypto_param_size;
1305
1306 /* Prepare command payload */
1307 i = 0;
1308 payload[i] = fcs_sha2_data_sign_param.session_id;
1309 i++;
1310 payload[i] = fcs_sha2_data_sign_param.context_id;
1311 i++;
1312 payload[i] = crypto_header;
1313 i++;
1314
1315 if ((crypto_header >> FCS_CS_FIELD_FLAG_OFFSET) &
1316 FCS_CS_FIELD_FLAG_INIT) {
1317 payload[i] = fcs_sha2_data_sign_param.key_id;
1318 /* Crypto parameters */
1319 i++;
1320 payload[i] = fcs_sha2_data_sign_param.crypto_param
1321 & INTEL_SIP_SMC_FCS_ECC_ALGO_MASK;
1322 i++;
1323 }
1324
1325 /* Data source address and size */
1326 payload[i] = src_addr;
1327 i++;
1328 payload[i] = src_size;
1329 i++;
1330 status = mailbox_send_cmd(MBOX_JOB_ID,
1331 MBOX_FCS_ECDSA_SHA2_DATA_SIGN_REQ, payload,
1332 i, CMD_CASUAL, (uint32_t *) dst_addr,
1333 &resp_len);
1334
1335 if (is_finalised != 0U) {
1336 memset((void *)&fcs_sha2_data_sign_param, 0,
1337 sizeof(fcs_crypto_service_data));
1338 }
1339
1340 if (status < 0) {
1341 *mbox_error = -status;
1342 return INTEL_SIP_SMC_STATUS_ERROR;
1343 }
1344
1345 *dst_size = resp_len * MBOX_WORD_BYTE;
1346 flush_dcache_range(dst_addr, *dst_size);
1347
1348 return INTEL_SIP_SMC_STATUS_OK;
1349 }
1350
intel_fcs_ecdsa_sha2_data_sig_verify_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)1351 int intel_fcs_ecdsa_sha2_data_sig_verify_init(uint32_t session_id,
1352 uint32_t context_id, uint32_t key_id,
1353 uint32_t param_size, uint64_t param_data,
1354 uint32_t *mbox_error)
1355 {
1356 return intel_fcs_crypto_service_init(session_id, context_id,
1357 key_id, param_size, param_data,
1358 (void *) &fcs_sha2_data_sig_verify_param,
1359 mbox_error);
1360 }
1361
intel_fcs_ecdsa_sha2_data_sig_verify_update_finalize(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint32_t data_size,uint8_t is_finalised,uint32_t * mbox_error)1362 int intel_fcs_ecdsa_sha2_data_sig_verify_update_finalize(uint32_t session_id,
1363 uint32_t context_id, uint32_t src_addr,
1364 uint32_t src_size, uint64_t dst_addr,
1365 uint32_t *dst_size, uint32_t data_size,
1366 uint8_t is_finalised, uint32_t *mbox_error)
1367 {
1368 int status;
1369 uint32_t i;
1370 uint32_t flag;
1371 uint32_t crypto_header;
1372 uint32_t payload[FCS_ECDSA_SHA2_DATA_SIG_VERIFY_CMD_MAX_WORD_SIZE] = {0U};
1373 uint32_t resp_len;
1374 uintptr_t sig_pubkey_offset;
1375
1376 if ((dst_size == NULL) || (mbox_error == NULL)) {
1377 return INTEL_SIP_SMC_STATUS_REJECTED;
1378 }
1379
1380 if (fcs_sha2_data_sig_verify_param.session_id != session_id ||
1381 fcs_sha2_data_sig_verify_param.context_id != context_id) {
1382 return INTEL_SIP_SMC_STATUS_REJECTED;
1383 }
1384
1385 if (!is_size_4_bytes_aligned(src_size)) {
1386 return INTEL_SIP_SMC_STATUS_REJECTED;
1387 }
1388
1389 if (!is_8_bytes_aligned(data_size) ||
1390 !is_8_bytes_aligned(src_addr)) {
1391 return INTEL_SIP_SMC_STATUS_REJECTED;
1392 }
1393
1394 if (!is_address_in_ddr_range(src_addr, src_size) ||
1395 !is_address_in_ddr_range(dst_addr, *dst_size)) {
1396 return INTEL_SIP_SMC_STATUS_REJECTED;
1397 }
1398
1399 resp_len = *dst_size / MBOX_WORD_BYTE;
1400
1401 /* Prepare crypto header */
1402 flag = 0;
1403 if (fcs_sha2_data_sig_verify_param.is_updated)
1404 fcs_sha2_data_sig_verify_param.crypto_param_size = 0;
1405 else
1406 flag |= FCS_CS_FIELD_FLAG_INIT;
1407
1408 if (is_finalised != 0U)
1409 flag |= FCS_CS_FIELD_FLAG_FINALIZE;
1410 else {
1411 flag |= FCS_CS_FIELD_FLAG_UPDATE;
1412 fcs_sha2_data_sig_verify_param.is_updated = 1;
1413 }
1414 crypto_header = (flag << FCS_CS_FIELD_FLAG_OFFSET) |
1415 fcs_sha2_data_sig_verify_param.crypto_param_size;
1416
1417 /* Prepare command payload */
1418 i = 0;
1419 payload[i] = fcs_sha2_data_sig_verify_param.session_id;
1420 i++;
1421 payload[i] = fcs_sha2_data_sig_verify_param.context_id;
1422 i++;
1423 payload[i] = crypto_header;
1424 i++;
1425
1426 if ((crypto_header >> FCS_CS_FIELD_FLAG_OFFSET) &
1427 FCS_CS_FIELD_FLAG_INIT) {
1428 payload[i] = fcs_sha2_data_sig_verify_param.key_id;
1429 i++;
1430 /* Crypto parameters */
1431 payload[i] = fcs_sha2_data_sig_verify_param.crypto_param
1432 & INTEL_SIP_SMC_FCS_ECC_ALGO_MASK;
1433 i++;
1434 }
1435
1436 /* Data source address and size */
1437 payload[i] = src_addr;
1438 i++;
1439 payload[i] = data_size;
1440 i++;
1441
1442 if ((crypto_header >> FCS_CS_FIELD_FLAG_OFFSET) &
1443 FCS_CS_FIELD_FLAG_FINALIZE) {
1444 /* Signature + Public Key Data */
1445 sig_pubkey_offset = src_addr + data_size;
1446 memcpy((uint8_t *) &payload[i], (uint8_t *) sig_pubkey_offset,
1447 src_size - data_size);
1448
1449 i += (src_size - data_size) / MBOX_WORD_BYTE;
1450 }
1451
1452 status = mailbox_send_cmd(MBOX_JOB_ID,
1453 MBOX_FCS_ECDSA_SHA2_DATA_SIGN_VERIFY, payload, i,
1454 CMD_CASUAL, (uint32_t *) dst_addr, &resp_len);
1455
1456 if (is_finalised != 0U) {
1457 memset((void *) &fcs_sha2_data_sig_verify_param, 0,
1458 sizeof(fcs_crypto_service_data));
1459 }
1460
1461 if (status < 0) {
1462 *mbox_error = -status;
1463 return INTEL_SIP_SMC_STATUS_ERROR;
1464 }
1465
1466 *dst_size = resp_len * MBOX_WORD_BYTE;
1467 flush_dcache_range(dst_addr, *dst_size);
1468
1469 return INTEL_SIP_SMC_STATUS_OK;
1470 }
1471
intel_fcs_ecdsa_get_pubkey_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)1472 int intel_fcs_ecdsa_get_pubkey_init(uint32_t session_id, uint32_t context_id,
1473 uint32_t key_id, uint32_t param_size,
1474 uint64_t param_data, uint32_t *mbox_error)
1475 {
1476 return intel_fcs_crypto_service_init(session_id, context_id,
1477 key_id, param_size, param_data,
1478 (void *) &fcs_ecdsa_get_pubkey_param,
1479 mbox_error);
1480 }
1481
intel_fcs_ecdsa_get_pubkey_finalize(uint32_t session_id,uint32_t context_id,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)1482 int intel_fcs_ecdsa_get_pubkey_finalize(uint32_t session_id, uint32_t context_id,
1483 uint64_t dst_addr, uint32_t *dst_size,
1484 uint32_t *mbox_error)
1485 {
1486 int status;
1487 int i;
1488 uint32_t crypto_header;
1489 uint32_t ret_size;
1490 uint32_t payload[FCS_ECDSA_GET_PUBKEY_MAX_WORD_SIZE] = {0U};
1491
1492 if ((dst_size == NULL) || (mbox_error == NULL)) {
1493 return INTEL_SIP_SMC_STATUS_REJECTED;
1494 }
1495
1496 if (fcs_ecdsa_get_pubkey_param.session_id != session_id ||
1497 fcs_ecdsa_get_pubkey_param.context_id != context_id) {
1498 return INTEL_SIP_SMC_STATUS_REJECTED;
1499 }
1500
1501 ret_size = *dst_size / MBOX_WORD_BYTE;
1502
1503 crypto_header = ((FCS_CS_FIELD_FLAG_INIT |
1504 FCS_CS_FIELD_FLAG_UPDATE |
1505 FCS_CS_FIELD_FLAG_FINALIZE) <<
1506 FCS_CS_FIELD_FLAG_OFFSET) |
1507 fcs_ecdsa_get_pubkey_param.crypto_param_size;
1508 i = 0;
1509 /* Prepare command payload */
1510 payload[i] = session_id;
1511 i++;
1512 payload[i] = context_id;
1513 i++;
1514 payload[i] = crypto_header;
1515 i++;
1516 payload[i] = fcs_ecdsa_get_pubkey_param.key_id;
1517 i++;
1518 payload[i] = (uint32_t) fcs_ecdsa_get_pubkey_param.crypto_param &
1519 INTEL_SIP_SMC_FCS_ECC_ALGO_MASK;
1520 i++;
1521
1522 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_ECDSA_GET_PUBKEY,
1523 payload, i, CMD_CASUAL,
1524 (uint32_t *) dst_addr, &ret_size);
1525
1526 memset((void *) &fcs_ecdsa_get_pubkey_param, 0,
1527 sizeof(fcs_crypto_service_data));
1528
1529 if (status < 0) {
1530 *mbox_error = -status;
1531 return INTEL_SIP_SMC_STATUS_ERROR;
1532 }
1533
1534 *dst_size = ret_size * MBOX_WORD_BYTE;
1535 flush_dcache_range(dst_addr, *dst_size);
1536
1537 return INTEL_SIP_SMC_STATUS_OK;
1538 }
1539
intel_fcs_ecdh_request_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint32_t param_size,uint64_t param_data,uint32_t * mbox_error)1540 int intel_fcs_ecdh_request_init(uint32_t session_id, uint32_t context_id,
1541 uint32_t key_id, uint32_t param_size,
1542 uint64_t param_data, uint32_t *mbox_error)
1543 {
1544 return intel_fcs_crypto_service_init(session_id, context_id,
1545 key_id, param_size, param_data,
1546 (void *) &fcs_ecdh_request_param,
1547 mbox_error);
1548 }
1549
intel_fcs_ecdh_request_finalize(uint32_t session_id,uint32_t context_id,uint32_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t * dst_size,uint32_t * mbox_error)1550 int intel_fcs_ecdh_request_finalize(uint32_t session_id, uint32_t context_id,
1551 uint32_t src_addr, uint32_t src_size,
1552 uint64_t dst_addr, uint32_t *dst_size,
1553 uint32_t *mbox_error)
1554 {
1555 int status;
1556 uint32_t i;
1557 uint32_t payload[FCS_ECDH_REQUEST_CMD_MAX_WORD_SIZE] = {0U};
1558 uint32_t resp_len;
1559 uintptr_t pubkey;
1560
1561 if ((dst_size == NULL) || (mbox_error == NULL)) {
1562 return INTEL_SIP_SMC_STATUS_REJECTED;
1563 }
1564
1565 if (fcs_ecdh_request_param.session_id != session_id ||
1566 fcs_ecdh_request_param.context_id != context_id) {
1567 return INTEL_SIP_SMC_STATUS_REJECTED;
1568 }
1569
1570 if (!is_address_in_ddr_range(src_addr, src_size) ||
1571 !is_address_in_ddr_range(dst_addr, *dst_size)) {
1572 return INTEL_SIP_SMC_STATUS_REJECTED;
1573 }
1574
1575 resp_len = *dst_size / MBOX_WORD_BYTE;
1576
1577 /* Prepare command payload */
1578 i = 0;
1579 /* Crypto header */
1580 payload[i] = fcs_ecdh_request_param.session_id;
1581 i++;
1582 payload[i] = fcs_ecdh_request_param.context_id;
1583 i++;
1584 payload[i] = fcs_ecdh_request_param.crypto_param_size
1585 & FCS_CS_FIELD_SIZE_MASK;
1586 payload[i] |= (FCS_CS_FIELD_FLAG_INIT | FCS_CS_FIELD_FLAG_UPDATE
1587 | FCS_CS_FIELD_FLAG_FINALIZE)
1588 << FCS_CS_FIELD_FLAG_OFFSET;
1589 i++;
1590 payload[i] = fcs_ecdh_request_param.key_id;
1591 i++;
1592 /* Crypto parameters */
1593 payload[i] = fcs_ecdh_request_param.crypto_param
1594 & INTEL_SIP_SMC_FCS_ECC_ALGO_MASK;
1595 i++;
1596 /* Public key data */
1597 pubkey = src_addr;
1598 memcpy((uint8_t *) &payload[i], (uint8_t *) pubkey, src_size);
1599 i += src_size / MBOX_WORD_BYTE;
1600
1601 status = mailbox_send_cmd(MBOX_JOB_ID, MBOX_FCS_ECDH_REQUEST,
1602 payload, i, CMD_CASUAL, (uint32_t *) dst_addr,
1603 &resp_len);
1604
1605 memset((void *)&fcs_ecdh_request_param, 0,
1606 sizeof(fcs_crypto_service_data));
1607
1608 if (status < 0) {
1609 *mbox_error = -status;
1610 return INTEL_SIP_SMC_STATUS_ERROR;
1611 }
1612
1613 *dst_size = resp_len * MBOX_WORD_BYTE;
1614 flush_dcache_range(dst_addr, *dst_size);
1615
1616 return INTEL_SIP_SMC_STATUS_OK;
1617 }
1618
intel_fcs_aes_crypt_init(uint32_t session_id,uint32_t context_id,uint32_t key_id,uint64_t param_addr,uint32_t param_size,uint32_t * mbox_error)1619 int intel_fcs_aes_crypt_init(uint32_t session_id, uint32_t context_id,
1620 uint32_t key_id, uint64_t param_addr,
1621 uint32_t param_size, uint32_t *mbox_error)
1622 {
1623 if (mbox_error == NULL) {
1624 return INTEL_SIP_SMC_STATUS_REJECTED;
1625 }
1626
1627 memset((void *)&fcs_aes_init_payload, 0U, sizeof(fcs_aes_init_payload));
1628
1629 fcs_aes_init_payload.session_id = session_id;
1630 fcs_aes_init_payload.context_id = context_id;
1631 fcs_aes_init_payload.param_size = param_size;
1632 fcs_aes_init_payload.key_id = key_id;
1633
1634 memcpy((uint8_t *) fcs_aes_init_payload.crypto_param,
1635 (uint8_t *) param_addr, param_size);
1636
1637 fcs_aes_init_payload.is_updated = 0;
1638
1639 *mbox_error = 0;
1640
1641 return INTEL_SIP_SMC_STATUS_OK;
1642 }
1643
intel_fcs_aes_crypt_update_finalize(uint32_t session_id,uint32_t context_id,uint64_t src_addr,uint32_t src_size,uint64_t dst_addr,uint32_t dst_size,uint8_t is_finalised,uint32_t * send_id)1644 int intel_fcs_aes_crypt_update_finalize(uint32_t session_id,
1645 uint32_t context_id, uint64_t src_addr,
1646 uint32_t src_size, uint64_t dst_addr,
1647 uint32_t dst_size, uint8_t is_finalised,
1648 uint32_t *send_id)
1649 {
1650 int status;
1651 int i;
1652 uint32_t flag;
1653 uint32_t crypto_header;
1654 uint32_t fcs_aes_crypt_payload[FCS_AES_CMD_MAX_WORD_SIZE];
1655
1656 if (fcs_aes_init_payload.session_id != session_id ||
1657 fcs_aes_init_payload.context_id != context_id) {
1658 return INTEL_SIP_SMC_STATUS_REJECTED;
1659 }
1660
1661 if ((!is_8_bytes_aligned(src_addr)) ||
1662 (!is_32_bytes_aligned(src_size)) ||
1663 (!is_address_in_ddr_range(src_addr, src_size))) {
1664 return INTEL_SIP_SMC_STATUS_REJECTED;
1665 }
1666
1667 if ((!is_8_bytes_aligned(dst_addr)) ||
1668 (!is_32_bytes_aligned(dst_size))) {
1669 return INTEL_SIP_SMC_STATUS_REJECTED;
1670 }
1671
1672 if ((dst_size > FCS_AES_MAX_DATA_SIZE ||
1673 dst_size < FCS_AES_MIN_DATA_SIZE) ||
1674 (src_size > FCS_AES_MAX_DATA_SIZE ||
1675 src_size < FCS_AES_MIN_DATA_SIZE)) {
1676 return INTEL_SIP_SMC_STATUS_REJECTED;
1677 }
1678
1679 /* Prepare crypto header*/
1680 flag = 0;
1681 if (fcs_aes_init_payload.is_updated) {
1682 fcs_aes_init_payload.param_size = 0;
1683 } else {
1684 flag |= FCS_CS_FIELD_FLAG_INIT;
1685 }
1686
1687 if (is_finalised != 0U) {
1688 flag |= FCS_CS_FIELD_FLAG_FINALIZE;
1689 } else {
1690 flag |= FCS_CS_FIELD_FLAG_UPDATE;
1691 fcs_aes_init_payload.is_updated = 1;
1692 }
1693 crypto_header = (flag << FCS_CS_FIELD_FLAG_OFFSET) |
1694 fcs_aes_init_payload.param_size;
1695
1696 i = 0U;
1697 fcs_aes_crypt_payload[i] = session_id;
1698 i++;
1699 fcs_aes_crypt_payload[i] = context_id;
1700 i++;
1701 fcs_aes_crypt_payload[i] = crypto_header;
1702 i++;
1703
1704 if ((crypto_header >> FCS_CS_FIELD_FLAG_OFFSET) &
1705 FCS_CS_FIELD_FLAG_INIT) {
1706 fcs_aes_crypt_payload[i] = fcs_aes_init_payload.key_id;
1707 i++;
1708
1709 memcpy((uint8_t *) &fcs_aes_crypt_payload[i],
1710 (uint8_t *) fcs_aes_init_payload.crypto_param,
1711 fcs_aes_init_payload.param_size);
1712
1713 i += fcs_aes_init_payload.param_size / MBOX_WORD_BYTE;
1714 }
1715
1716 fcs_aes_crypt_payload[i] = (uint32_t) src_addr;
1717 i++;
1718 fcs_aes_crypt_payload[i] = src_size;
1719 i++;
1720 fcs_aes_crypt_payload[i] = (uint32_t) dst_addr;
1721 i++;
1722 fcs_aes_crypt_payload[i] = dst_size;
1723 i++;
1724
1725 status = mailbox_send_cmd_async(send_id, MBOX_FCS_AES_CRYPT_REQ,
1726 fcs_aes_crypt_payload, i,
1727 CMD_INDIRECT);
1728
1729 if (is_finalised != 0U) {
1730 memset((void *)&fcs_aes_init_payload, 0,
1731 sizeof(fcs_aes_init_payload));
1732 }
1733
1734 if (status < 0U) {
1735 return INTEL_SIP_SMC_STATUS_ERROR;
1736 }
1737
1738 return INTEL_SIP_SMC_STATUS_OK;
1739 }
1740