xref: /optee_os/ta/pkcs11/src/pkcs11_token.c (revision c04a96a45ffe0e665a4d86e542ec921fae932aa8)
1 // SPDX-License-Identifier: BSD-2-Clause
2 /*
3  * Copyright (c) 2017-2020, Linaro Limited
4  */
5 
6 #include <assert.h>
7 #include <config.h>
8 #include <confine_array_index.h>
9 #include <pkcs11_ta.h>
10 #include <printk.h>
11 #include <pta_system.h>
12 #include <string.h>
13 #include <string_ext.h>
14 #include <sys/queue.h>
15 #include <tee_api_types.h>
16 #include <tee_internal_api_extensions.h>
17 #include <util.h>
18 
19 #include "attributes.h"
20 #include "handle.h"
21 #include "pkcs11_helpers.h"
22 #include "pkcs11_token.h"
23 #include "processing.h"
24 #include "serializer.h"
25 #include "token_capabilities.h"
26 
27 /* Provide 3 slots/tokens, ID is token index */
28 #ifndef CFG_PKCS11_TA_TOKEN_COUNT
29 #define TOKEN_COUNT		3
30 #else
31 #define TOKEN_COUNT		CFG_PKCS11_TA_TOKEN_COUNT
32 #endif
33 
34 /* RNG chunk size used to split RNG generation to smaller sizes */
35 #define RNG_CHUNK_SIZE		512U
36 
37 /*
38  * Structure tracking client applications
39  *
40  * @link - chained list of registered client applications
41  * @sessions - list of the PKCS11 sessions opened by the client application
42  * @object_handle_db - Database for object handles in name space of client
43  */
44 struct pkcs11_client {
45 	TAILQ_ENTRY(pkcs11_client) link;
46 	struct session_list session_list;
47 	struct handle_db session_handle_db;
48 	struct handle_db object_handle_db;
49 };
50 
51 /* Static allocation of tokens runtime instances (reset to 0 at load) */
52 struct ck_token ck_token[TOKEN_COUNT];
53 
54 static struct client_list pkcs11_client_list =
55 	TAILQ_HEAD_INITIALIZER(pkcs11_client_list);
56 
57 static void close_ck_session(struct pkcs11_session *session);
58 
59 struct ck_token *get_token(unsigned int token_id)
60 {
61 	if (token_id < TOKEN_COUNT)
62 		return &ck_token[confine_array_index(token_id, TOKEN_COUNT)];
63 
64 	return NULL;
65 }
66 
67 unsigned int get_token_id(struct ck_token *token)
68 {
69 	ptrdiff_t id = token - ck_token;
70 
71 	assert(id >= 0 && id < TOKEN_COUNT);
72 	return id;
73 }
74 
75 struct handle_db *get_object_handle_db(struct pkcs11_session *session)
76 {
77 	return &session->client->object_handle_db;
78 }
79 
80 struct session_list *get_session_list(struct pkcs11_session *session)
81 {
82 	return &session->client->session_list;
83 }
84 
85 struct pkcs11_client *tee_session2client(void *tee_session)
86 {
87 	struct pkcs11_client *client = NULL;
88 
89 	TAILQ_FOREACH(client, &pkcs11_client_list, link)
90 		if (client == tee_session)
91 			break;
92 
93 	return client;
94 }
95 
96 struct pkcs11_session *pkcs11_handle2session(uint32_t handle,
97 					     struct pkcs11_client *client)
98 {
99 	return handle_lookup(&client->session_handle_db, handle);
100 }
101 
102 struct pkcs11_client *register_client(void)
103 {
104 	struct pkcs11_client *client = NULL;
105 
106 	client = TEE_Malloc(sizeof(*client), TEE_MALLOC_FILL_ZERO);
107 	if (!client)
108 		return NULL;
109 
110 	TAILQ_INSERT_HEAD(&pkcs11_client_list, client, link);
111 	TAILQ_INIT(&client->session_list);
112 	handle_db_init(&client->session_handle_db);
113 	handle_db_init(&client->object_handle_db);
114 
115 	return client;
116 }
117 
118 void unregister_client(struct pkcs11_client *client)
119 {
120 	struct pkcs11_session *session = NULL;
121 	struct pkcs11_session *next = NULL;
122 
123 	if (!client) {
124 		EMSG("Invalid TEE session handle");
125 		return;
126 	}
127 
128 	TAILQ_FOREACH_SAFE(session, &client->session_list, link, next)
129 		close_ck_session(session);
130 
131 	TAILQ_REMOVE(&pkcs11_client_list, client, link);
132 	handle_db_destroy(&client->object_handle_db);
133 	handle_db_destroy(&client->session_handle_db);
134 	TEE_Free(client);
135 }
136 
137 static TEE_Result pkcs11_token_init(unsigned int id)
138 {
139 	struct ck_token *token = init_persistent_db(id);
140 
141 	if (!token)
142 		return TEE_ERROR_SECURITY;
143 
144 	if (token->state == PKCS11_TOKEN_RESET) {
145 		/* As per PKCS#11 spec, token resets to read/write state */
146 		token->state = PKCS11_TOKEN_READ_WRITE;
147 		token->session_count = 0;
148 		token->rw_session_count = 0;
149 	}
150 
151 	return TEE_SUCCESS;
152 }
153 
154 TEE_Result pkcs11_init(void)
155 {
156 	unsigned int id = 0;
157 	TEE_Result ret = TEE_ERROR_GENERIC;
158 
159 	for (id = 0; id < TOKEN_COUNT; id++) {
160 		ret = pkcs11_token_init(id);
161 		if (ret)
162 			break;
163 	}
164 
165 	return ret;
166 }
167 
168 void pkcs11_deinit(void)
169 {
170 	unsigned int id = 0;
171 
172 	for (id = 0; id < TOKEN_COUNT; id++)
173 		close_persistent_db(get_token(id));
174 }
175 
176 /*
177  * Currently no support for dual operations.
178  */
179 enum pkcs11_rc set_processing_state(struct pkcs11_session *session,
180 				    enum processing_func function,
181 				    struct pkcs11_object *obj1,
182 				    struct pkcs11_object *obj2)
183 {
184 	enum pkcs11_proc_state state = PKCS11_SESSION_READY;
185 	struct active_processing *proc = NULL;
186 
187 	if (session->processing)
188 		return PKCS11_CKR_OPERATION_ACTIVE;
189 
190 	switch (function) {
191 	case PKCS11_FUNCTION_ENCRYPT:
192 		state = PKCS11_SESSION_ENCRYPTING;
193 		break;
194 	case PKCS11_FUNCTION_DECRYPT:
195 		state = PKCS11_SESSION_DECRYPTING;
196 		break;
197 	case PKCS11_FUNCTION_SIGN:
198 		state = PKCS11_SESSION_SIGNING;
199 		break;
200 	case PKCS11_FUNCTION_VERIFY:
201 		state = PKCS11_SESSION_VERIFYING;
202 		break;
203 	case PKCS11_FUNCTION_DIGEST:
204 		state = PKCS11_SESSION_DIGESTING;
205 		break;
206 	case PKCS11_FUNCTION_DERIVE:
207 		state = PKCS11_SESSION_READY;
208 		break;
209 	default:
210 		TEE_Panic(function);
211 		return -1;
212 	}
213 
214 	proc = TEE_Malloc(sizeof(*proc), TEE_MALLOC_FILL_ZERO);
215 	if (!proc)
216 		return PKCS11_CKR_DEVICE_MEMORY;
217 
218 	/* Boolean are default to false and pointers to NULL */
219 	proc->state = state;
220 	proc->tee_op_handle = TEE_HANDLE_NULL;
221 
222 	if (obj1 && get_bool(obj1->attributes, PKCS11_CKA_ALWAYS_AUTHENTICATE))
223 		proc->always_authen = true;
224 
225 	if (obj2 && get_bool(obj2->attributes, PKCS11_CKA_ALWAYS_AUTHENTICATE))
226 		proc->always_authen = true;
227 
228 	session->processing = proc;
229 
230 	return PKCS11_CKR_OK;
231 }
232 
233 enum pkcs11_rc entry_ck_slot_list(uint32_t ptypes, TEE_Param *params)
234 {
235 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
236 						TEE_PARAM_TYPE_NONE,
237 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
238 						TEE_PARAM_TYPE_NONE);
239 	TEE_Param *out = params + 2;
240 	uint32_t token_id = 0;
241 	const size_t out_size = sizeof(token_id) * TOKEN_COUNT;
242 	uint8_t *id = NULL;
243 
244 	if (ptypes != exp_pt ||
245 	    params[0].memref.size != TEE_PARAM0_SIZE_MIN)
246 		return PKCS11_CKR_ARGUMENTS_BAD;
247 
248 	if (out->memref.size < out_size) {
249 		out->memref.size = out_size;
250 
251 		if (out->memref.buffer)
252 			return PKCS11_CKR_BUFFER_TOO_SMALL;
253 		else
254 			return PKCS11_CKR_OK;
255 	}
256 
257 	for (token_id = 0, id = out->memref.buffer; token_id < TOKEN_COUNT;
258 	     token_id++, id += sizeof(token_id))
259 		TEE_MemMove(id, &token_id, sizeof(token_id));
260 
261 	out->memref.size = out_size;
262 
263 	return PKCS11_CKR_OK;
264 }
265 
266 static void pad_str(uint8_t *str, size_t size)
267 {
268 	int n = strnlen((char *)str, size);
269 
270 	TEE_MemFill(str + n, ' ', size - n);
271 }
272 
273 static void set_token_description(struct pkcs11_slot_info *info)
274 {
275 	char desc[sizeof(info->slot_description) + 1] = { 0 };
276 	TEE_UUID dev_id = { };
277 	TEE_Result res = TEE_ERROR_GENERIC;
278 	int n = 0;
279 
280 	res = TEE_GetPropertyAsUUID(TEE_PROPSET_TEE_IMPLEMENTATION,
281 				    "gpd.tee.deviceID", &dev_id);
282 	if (res == TEE_SUCCESS) {
283 		n = snprintk(desc, sizeof(desc), PKCS11_SLOT_DESCRIPTION
284 			     " - TEE UUID %pUl", (void *)&dev_id);
285 	} else {
286 		n = snprintf(desc, sizeof(desc), PKCS11_SLOT_DESCRIPTION
287 			     " - No TEE UUID");
288 	}
289 	if (n < 0 || n >= (int)sizeof(desc))
290 		TEE_Panic(0);
291 
292 	TEE_MemMove(info->slot_description, desc, n);
293 	pad_str(info->slot_description, sizeof(info->slot_description));
294 }
295 
296 enum pkcs11_rc entry_ck_slot_info(uint32_t ptypes, TEE_Param *params)
297 {
298 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
299 						TEE_PARAM_TYPE_NONE,
300 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
301 						TEE_PARAM_TYPE_NONE);
302 	TEE_Param *ctrl = params;
303 	TEE_Param *out = params + 2;
304 	enum pkcs11_rc rc = PKCS11_CKR_OK;
305 	struct serialargs ctrlargs = { };
306 	uint32_t token_id = 0;
307 	struct pkcs11_slot_info info = {
308 		.slot_description = PKCS11_SLOT_DESCRIPTION,
309 		.manufacturer_id = PKCS11_SLOT_MANUFACTURER,
310 		.flags = PKCS11_CKFS_TOKEN_PRESENT,
311 		.hardware_version = PKCS11_SLOT_HW_VERSION,
312 		.firmware_version = PKCS11_SLOT_FW_VERSION,
313 	};
314 
315 	COMPILE_TIME_ASSERT(sizeof(PKCS11_SLOT_DESCRIPTION) <=
316 			    sizeof(info.slot_description));
317 	COMPILE_TIME_ASSERT(sizeof(PKCS11_SLOT_MANUFACTURER) <=
318 			    sizeof(info.manufacturer_id));
319 
320 	if (ptypes != exp_pt || out->memref.size != sizeof(info))
321 		return PKCS11_CKR_ARGUMENTS_BAD;
322 
323 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
324 
325 	rc = serialargs_get(&ctrlargs, &token_id, sizeof(token_id));
326 	if (rc)
327 		return rc;
328 
329 	if (serialargs_remaining_bytes(&ctrlargs))
330 		return PKCS11_CKR_ARGUMENTS_BAD;
331 
332 	if (!get_token(token_id))
333 		return PKCS11_CKR_SLOT_ID_INVALID;
334 
335 	set_token_description(&info);
336 
337 	pad_str(info.manufacturer_id, sizeof(info.manufacturer_id));
338 
339 	out->memref.size = sizeof(info);
340 	TEE_MemMove(out->memref.buffer, &info, out->memref.size);
341 
342 	return PKCS11_CKR_OK;
343 }
344 
345 enum pkcs11_rc entry_ck_token_info(uint32_t ptypes, TEE_Param *params)
346 {
347 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
348 						TEE_PARAM_TYPE_NONE,
349 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
350 						TEE_PARAM_TYPE_NONE);
351 	TEE_Param *ctrl = params;
352 	TEE_Param *out = params + 2;
353 	enum pkcs11_rc rc = PKCS11_CKR_OK;
354 	struct serialargs ctrlargs = { };
355 	uint32_t token_id = 0;
356 	struct ck_token *token = NULL;
357 	struct pkcs11_token_info info = {
358 		.manufacturer_id = PKCS11_TOKEN_MANUFACTURER,
359 		.model = PKCS11_TOKEN_MODEL,
360 		.max_session_count = UINT32_MAX,
361 		.max_rw_session_count = UINT32_MAX,
362 		.max_pin_len = PKCS11_TOKEN_PIN_SIZE_MAX,
363 		.min_pin_len = PKCS11_TOKEN_PIN_SIZE_MIN,
364 		.total_public_memory = UINT32_MAX,
365 		.free_public_memory = UINT32_MAX,
366 		.total_private_memory = UINT32_MAX,
367 		.free_private_memory = UINT32_MAX,
368 		.hardware_version = PKCS11_TOKEN_HW_VERSION,
369 		.firmware_version = PKCS11_TOKEN_FW_VERSION,
370 	};
371 	char sn[sizeof(info.serial_number) + 1] = { 0 };
372 	int n = 0;
373 
374 	if (ptypes != exp_pt || out->memref.size != sizeof(info))
375 		return PKCS11_CKR_ARGUMENTS_BAD;
376 
377 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
378 
379 	rc = serialargs_get(&ctrlargs, &token_id, sizeof(token_id));
380 	if (rc)
381 		return rc;
382 
383 	if (serialargs_remaining_bytes(&ctrlargs))
384 		return PKCS11_CKR_ARGUMENTS_BAD;
385 
386 	token = get_token(token_id);
387 	if (!token)
388 		return PKCS11_CKR_SLOT_ID_INVALID;
389 
390 	pad_str(info.manufacturer_id, sizeof(info.manufacturer_id));
391 	pad_str(info.model, sizeof(info.model));
392 
393 	n = snprintf(sn, sizeof(sn), "%0*"PRIu32,
394 		     (int)sizeof(info.serial_number), token_id);
395 	if (n != (int)sizeof(info.serial_number))
396 		TEE_Panic(0);
397 
398 	TEE_MemMove(info.serial_number, sn, sizeof(info.serial_number));
399 	pad_str(info.serial_number, sizeof(info.serial_number));
400 
401 	TEE_MemMove(info.label, token->db_main->label, sizeof(info.label));
402 
403 	info.flags = token->db_main->flags;
404 	info.session_count = token->session_count;
405 	info.rw_session_count = token->rw_session_count;
406 
407 	TEE_MemMove(out->memref.buffer, &info, sizeof(info));
408 
409 	return PKCS11_CKR_OK;
410 }
411 
412 static void dmsg_print_supported_mechanism(unsigned int token_id __maybe_unused,
413 					   uint32_t *array __maybe_unused,
414 					   size_t count __maybe_unused)
415 {
416 	size_t __maybe_unused n = 0;
417 
418 	if (TRACE_LEVEL < TRACE_DEBUG)
419 		return;
420 
421 	for (n = 0; n < count; n++)
422 		DMSG("PKCS11 token %"PRIu32": mechanism 0x%04"PRIx32": %s",
423 		     token_id, array[n], id2str_mechanism(array[n]));
424 }
425 
426 enum pkcs11_rc entry_ck_token_mecha_ids(uint32_t ptypes, TEE_Param *params)
427 {
428 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
429 						TEE_PARAM_TYPE_NONE,
430 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
431 						TEE_PARAM_TYPE_NONE);
432 	TEE_Param *ctrl = params;
433 	TEE_Param *out = params + 2;
434 	enum pkcs11_rc rc = PKCS11_CKR_OK;
435 	struct serialargs ctrlargs = { };
436 	uint32_t token_id = 0;
437 	struct ck_token __maybe_unused *token = NULL;
438 	size_t count = 0;
439 	uint32_t *array = NULL;
440 
441 	if (ptypes != exp_pt)
442 		return PKCS11_CKR_ARGUMENTS_BAD;
443 
444 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
445 
446 	rc = serialargs_get(&ctrlargs, &token_id, sizeof(token_id));
447 	if (rc)
448 		return rc;
449 
450 	if (serialargs_remaining_bytes(&ctrlargs))
451 		return PKCS11_CKR_ARGUMENTS_BAD;
452 
453 	token = get_token(token_id);
454 	if (!token)
455 		return PKCS11_CKR_SLOT_ID_INVALID;
456 
457 	count = out->memref.size / sizeof(*array);
458 	array = tee_malloc_mechanism_list(&count);
459 
460 	if (out->memref.size < count * sizeof(*array)) {
461 		assert(!array);
462 		out->memref.size = count * sizeof(*array);
463 		if (out->memref.buffer)
464 			return PKCS11_CKR_BUFFER_TOO_SMALL;
465 		else
466 			return PKCS11_CKR_OK;
467 	}
468 
469 	if (!array)
470 		return PKCS11_CKR_DEVICE_MEMORY;
471 
472 	dmsg_print_supported_mechanism(token_id, array, count);
473 
474 	out->memref.size = count * sizeof(*array);
475 	TEE_MemMove(out->memref.buffer, array, out->memref.size);
476 
477 	TEE_Free(array);
478 
479 	return rc;
480 }
481 
482 enum pkcs11_rc entry_ck_token_mecha_info(uint32_t ptypes, TEE_Param *params)
483 {
484 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
485 						TEE_PARAM_TYPE_NONE,
486 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
487 						TEE_PARAM_TYPE_NONE);
488 	TEE_Param *ctrl = params;
489 	TEE_Param *out = params + 2;
490 	enum pkcs11_rc rc = PKCS11_CKR_OK;
491 	struct serialargs ctrlargs = { };
492 	uint32_t token_id = 0;
493 	uint32_t type = 0;
494 	struct ck_token *token = NULL;
495 	struct pkcs11_mechanism_info info = { };
496 
497 	if (ptypes != exp_pt || out->memref.size != sizeof(info))
498 		return PKCS11_CKR_ARGUMENTS_BAD;
499 
500 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
501 
502 	rc = serialargs_get(&ctrlargs, &token_id, sizeof(uint32_t));
503 	if (rc)
504 		return rc;
505 
506 	rc = serialargs_get(&ctrlargs, &type, sizeof(uint32_t));
507 	if (rc)
508 		return rc;
509 
510 	if (serialargs_remaining_bytes(&ctrlargs))
511 		return PKCS11_CKR_ARGUMENTS_BAD;
512 
513 	token = get_token(token_id);
514 	if (!token)
515 		return PKCS11_CKR_SLOT_ID_INVALID;
516 
517 	if (!mechanism_is_valid(type))
518 		return PKCS11_CKR_MECHANISM_INVALID;
519 
520 	info.flags = mechanism_supported_flags(type);
521 
522 	pkcs11_mechanism_supported_key_sizes(type, &info.min_key_size,
523 					     &info.max_key_size);
524 
525 	TEE_MemMove(out->memref.buffer, &info, sizeof(info));
526 
527 	DMSG("PKCS11 token %"PRIu32": mechanism 0x%"PRIx32" info",
528 	     token_id, type);
529 
530 	return PKCS11_CKR_OK;
531 }
532 
533 /* Select the ReadOnly or ReadWrite state for session login state */
534 static void set_session_state(struct pkcs11_client *client,
535 			      struct pkcs11_session *session, bool readonly)
536 {
537 	struct pkcs11_session *sess = NULL;
538 	enum pkcs11_session_state state = PKCS11_CKS_RO_PUBLIC_SESSION;
539 
540 	/* Default to public session if no session already registered */
541 	if (readonly)
542 		state = PKCS11_CKS_RO_PUBLIC_SESSION;
543 	else
544 		state = PKCS11_CKS_RW_PUBLIC_SESSION;
545 
546 	/*
547 	 * No need to check all client sessions, the first found in
548 	 * target token gives client login configuration.
549 	 */
550 	TAILQ_FOREACH(sess, &client->session_list, link) {
551 		assert(sess != session);
552 
553 		if (sess->token == session->token) {
554 			switch (sess->state) {
555 			case PKCS11_CKS_RW_PUBLIC_SESSION:
556 			case PKCS11_CKS_RO_PUBLIC_SESSION:
557 				if (readonly)
558 					state = PKCS11_CKS_RO_PUBLIC_SESSION;
559 				else
560 					state = PKCS11_CKS_RW_PUBLIC_SESSION;
561 				break;
562 			case PKCS11_CKS_RO_USER_FUNCTIONS:
563 			case PKCS11_CKS_RW_USER_FUNCTIONS:
564 				if (readonly)
565 					state = PKCS11_CKS_RO_USER_FUNCTIONS;
566 				else
567 					state = PKCS11_CKS_RW_USER_FUNCTIONS;
568 				break;
569 			case PKCS11_CKS_RW_SO_FUNCTIONS:
570 				if (readonly)
571 					TEE_Panic(0);
572 				else
573 					state = PKCS11_CKS_RW_SO_FUNCTIONS;
574 				break;
575 			default:
576 				TEE_Panic(0);
577 			}
578 			break;
579 		}
580 	}
581 
582 	session->state = state;
583 }
584 
585 enum pkcs11_rc entry_ck_open_session(struct pkcs11_client *client,
586 				     uint32_t ptypes, TEE_Param *params)
587 {
588 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
589 						TEE_PARAM_TYPE_NONE,
590 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
591 						TEE_PARAM_TYPE_NONE);
592 	TEE_Param *ctrl = params;
593 	TEE_Param *out = params + 2;
594 	enum pkcs11_rc rc = PKCS11_CKR_OK;
595 	struct serialargs ctrlargs = { };
596 	uint32_t token_id = 0;
597 	uint32_t flags = 0;
598 	struct ck_token *token = NULL;
599 	struct pkcs11_session *session = NULL;
600 	bool readonly = false;
601 
602 	if (!client || ptypes != exp_pt ||
603 	    out->memref.size != sizeof(session->handle))
604 		return PKCS11_CKR_ARGUMENTS_BAD;
605 
606 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
607 
608 	rc = serialargs_get(&ctrlargs, &token_id, sizeof(token_id));
609 	if (rc)
610 		return rc;
611 
612 	rc = serialargs_get(&ctrlargs, &flags, sizeof(flags));
613 	if (rc)
614 		return rc;
615 
616 	if (serialargs_remaining_bytes(&ctrlargs))
617 		return PKCS11_CKR_ARGUMENTS_BAD;
618 
619 	token = get_token(token_id);
620 	if (!token)
621 		return PKCS11_CKR_SLOT_ID_INVALID;
622 
623 	/* Sanitize session flags */
624 	if (!(flags & PKCS11_CKFSS_SERIAL_SESSION))
625 		return PKCS11_CKR_SESSION_PARALLEL_NOT_SUPPORTED;
626 
627 	if (flags & ~(PKCS11_CKFSS_RW_SESSION | PKCS11_CKFSS_SERIAL_SESSION))
628 		return PKCS11_CKR_ARGUMENTS_BAD;
629 
630 	readonly = !(flags & PKCS11_CKFSS_RW_SESSION);
631 
632 	if (!readonly && token->state == PKCS11_TOKEN_READ_ONLY)
633 		return PKCS11_CKR_TOKEN_WRITE_PROTECTED;
634 
635 	if (readonly) {
636 		/* Specifically reject read-only session under SO login */
637 		TAILQ_FOREACH(session, &client->session_list, link)
638 			if (pkcs11_session_is_so(session))
639 				return PKCS11_CKR_SESSION_READ_WRITE_SO_EXISTS;
640 	}
641 
642 	session = TEE_Malloc(sizeof(*session), TEE_MALLOC_FILL_ZERO);
643 	if (!session)
644 		return PKCS11_CKR_DEVICE_MEMORY;
645 
646 	session->handle = handle_get(&client->session_handle_db, session);
647 	if (!session->handle) {
648 		TEE_Free(session);
649 		return PKCS11_CKR_DEVICE_MEMORY;
650 	}
651 
652 	session->token = token;
653 	session->client = client;
654 
655 	LIST_INIT(&session->object_list);
656 
657 	set_session_state(client, session, readonly);
658 
659 	TAILQ_INSERT_HEAD(&client->session_list, session, link);
660 
661 	session->token->session_count++;
662 	if (!readonly)
663 		session->token->rw_session_count++;
664 
665 	TEE_MemMove(out->memref.buffer, &session->handle,
666 		    sizeof(session->handle));
667 
668 	DMSG("Open PKCS11 session %"PRIu32, session->handle);
669 
670 	return PKCS11_CKR_OK;
671 }
672 
673 static void close_ck_session(struct pkcs11_session *session)
674 {
675 	release_active_processing(session);
676 	release_session_find_obj_context(session);
677 
678 	/* Release all session objects */
679 	while (!LIST_EMPTY(&session->object_list))
680 		destroy_object(session,
681 			       LIST_FIRST(&session->object_list), true);
682 
683 	TAILQ_REMOVE(&session->client->session_list, session, link);
684 	handle_put(&session->client->session_handle_db, session->handle);
685 
686 	session->token->session_count--;
687 	if (pkcs11_session_is_read_write(session))
688 		session->token->rw_session_count--;
689 
690 	TEE_Free(session);
691 
692 	DMSG("Close PKCS11 session %"PRIu32, session->handle);
693 }
694 
695 enum pkcs11_rc entry_ck_close_session(struct pkcs11_client *client,
696 				      uint32_t ptypes, TEE_Param *params)
697 {
698 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
699 						TEE_PARAM_TYPE_NONE,
700 						TEE_PARAM_TYPE_NONE,
701 						TEE_PARAM_TYPE_NONE);
702 	TEE_Param *ctrl = params;
703 	enum pkcs11_rc rc = PKCS11_CKR_OK;
704 	struct serialargs ctrlargs = { };
705 	struct pkcs11_session *session = NULL;
706 
707 	if (!client || ptypes != exp_pt)
708 		return PKCS11_CKR_ARGUMENTS_BAD;
709 
710 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
711 
712 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
713 	if (rc)
714 		return rc;
715 
716 	if (serialargs_remaining_bytes(&ctrlargs))
717 		return PKCS11_CKR_ARGUMENTS_BAD;
718 
719 	close_ck_session(session);
720 
721 	return PKCS11_CKR_OK;
722 }
723 
724 enum pkcs11_rc entry_ck_close_all_sessions(struct pkcs11_client *client,
725 					   uint32_t ptypes, TEE_Param *params)
726 {
727 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
728 						TEE_PARAM_TYPE_NONE,
729 						TEE_PARAM_TYPE_NONE,
730 						TEE_PARAM_TYPE_NONE);
731 	TEE_Param *ctrl = params;
732 	enum pkcs11_rc rc = PKCS11_CKR_OK;
733 	struct serialargs ctrlargs = { };
734 	uint32_t token_id = 0;
735 	struct ck_token *token = NULL;
736 	struct pkcs11_session *session = NULL;
737 	struct pkcs11_session *next = NULL;
738 
739 	if (!client || ptypes != exp_pt)
740 		return PKCS11_CKR_ARGUMENTS_BAD;
741 
742 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
743 
744 	rc = serialargs_get(&ctrlargs, &token_id, sizeof(uint32_t));
745 	if (rc)
746 		return rc;
747 
748 	if (serialargs_remaining_bytes(&ctrlargs))
749 		return PKCS11_CKR_ARGUMENTS_BAD;
750 
751 	token = get_token(token_id);
752 	if (!token)
753 		return PKCS11_CKR_SLOT_ID_INVALID;
754 
755 	DMSG("Close all sessions for PKCS11 token %"PRIu32, token_id);
756 
757 	TAILQ_FOREACH_SAFE(session, &client->session_list, link, next)
758 		if (session->token == token)
759 			close_ck_session(session);
760 
761 	return PKCS11_CKR_OK;
762 }
763 
764 enum pkcs11_rc entry_ck_session_info(struct pkcs11_client *client,
765 				     uint32_t ptypes, TEE_Param *params)
766 {
767 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
768 						TEE_PARAM_TYPE_NONE,
769 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
770 						TEE_PARAM_TYPE_NONE);
771 	TEE_Param *ctrl = params;
772 	TEE_Param *out = params + 2;
773 	enum pkcs11_rc rc = PKCS11_CKR_OK;
774 	struct serialargs ctrlargs = { };
775 	struct pkcs11_session *session = NULL;
776 	struct pkcs11_session_info info = {
777 		.flags = PKCS11_CKFSS_SERIAL_SESSION,
778 	};
779 
780 	if (!client || ptypes != exp_pt || out->memref.size != sizeof(info))
781 		return PKCS11_CKR_ARGUMENTS_BAD;
782 
783 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
784 
785 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
786 	if (rc)
787 		return rc;
788 
789 	if (serialargs_remaining_bytes(&ctrlargs))
790 		return PKCS11_CKR_ARGUMENTS_BAD;
791 
792 	info.slot_id = get_token_id(session->token);
793 	info.state = session->state;
794 	if (pkcs11_session_is_read_write(session))
795 		info.flags |= PKCS11_CKFSS_RW_SESSION;
796 
797 	TEE_MemMove(out->memref.buffer, &info, sizeof(info));
798 
799 	DMSG("Get find on PKCS11 session %"PRIu32, session->handle);
800 
801 	return PKCS11_CKR_OK;
802 }
803 
804 enum pkcs11_rc entry_ck_token_initialize(uint32_t ptypes, TEE_Param *params)
805 {
806 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
807 						TEE_PARAM_TYPE_NONE,
808 						TEE_PARAM_TYPE_NONE,
809 						TEE_PARAM_TYPE_NONE);
810 	char label[PKCS11_TOKEN_LABEL_SIZE] = { 0 };
811 	struct pkcs11_client *client = NULL;
812 	struct pkcs11_session *sess = NULL;
813 	enum pkcs11_rc rc = PKCS11_CKR_OK;
814 	struct serialargs ctrlargs = { };
815 	struct ck_token *token = NULL;
816 	TEE_Param *ctrl = params;
817 	uint32_t token_id = 0;
818 	uint32_t pin_size = 0;
819 	void *pin = NULL;
820 	struct pkcs11_object *obj = NULL;
821 
822 	if (ptypes != exp_pt)
823 		return PKCS11_CKR_ARGUMENTS_BAD;
824 
825 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
826 
827 	rc = serialargs_get(&ctrlargs, &token_id, sizeof(uint32_t));
828 	if (rc)
829 		return rc;
830 
831 	rc = serialargs_get(&ctrlargs, &pin_size, sizeof(uint32_t));
832 	if (rc)
833 		return rc;
834 
835 	rc = serialargs_get(&ctrlargs, &label, PKCS11_TOKEN_LABEL_SIZE);
836 	if (rc)
837 		return rc;
838 
839 	rc = serialargs_get_ptr(&ctrlargs, &pin, pin_size);
840 	if (rc)
841 		return rc;
842 
843 	if (serialargs_remaining_bytes(&ctrlargs))
844 		return PKCS11_CKR_ARGUMENTS_BAD;
845 
846 	token = get_token(token_id);
847 	if (!token)
848 		return PKCS11_CKR_SLOT_ID_INVALID;
849 
850 	if (token->db_main->flags & PKCS11_CKFT_SO_PIN_LOCKED) {
851 		IMSG("Token %"PRIu32": SO PIN locked", token_id);
852 		return PKCS11_CKR_PIN_LOCKED;
853 	}
854 
855 	/* Check there's no open session on this token */
856 	TAILQ_FOREACH(client, &pkcs11_client_list, link)
857 		TAILQ_FOREACH(sess, &client->session_list, link)
858 			if (sess->token == token)
859 				return PKCS11_CKR_SESSION_EXISTS;
860 
861 #if defined(CFG_PKCS11_TA_AUTH_TEE_IDENTITY)
862 	/* Check TEE Identity based authentication if enabled */
863 	if (token->db_main->flags & PKCS11_CKFT_PROTECTED_AUTHENTICATION_PATH) {
864 		rc = verify_identity_auth(token, PKCS11_CKU_SO);
865 		if (rc)
866 			return rc;
867 	}
868 
869 	/* Detect TEE Identity based ACL usage activation with NULL PIN */
870 	if (!pin) {
871 		rc = setup_so_identity_auth_from_client(token);
872 		if (rc)
873 			return rc;
874 
875 		goto inited;
876 	} else {
877 		/* De-activate TEE Identity based authentication */
878 		token->db_main->flags &=
879 			~PKCS11_CKFT_PROTECTED_AUTHENTICATION_PATH;
880 	}
881 #endif /* CFG_PKCS11_TA_AUTH_TEE_IDENTITY */
882 
883 	if (!token->db_main->so_pin_salt) {
884 		/*
885 		 * The spec doesn't permit returning
886 		 * PKCS11_CKR_PIN_LEN_RANGE for this function, take another
887 		 * error code.
888 		 */
889 		if (pin_size < PKCS11_TOKEN_PIN_SIZE_MIN ||
890 		    pin_size > PKCS11_TOKEN_PIN_SIZE_MAX)
891 			return PKCS11_CKR_ARGUMENTS_BAD;
892 
893 		rc = hash_pin(PKCS11_CKU_SO, pin, pin_size,
894 			      &token->db_main->so_pin_salt,
895 			      token->db_main->so_pin_hash);
896 		if (rc)
897 			return rc;
898 
899 		goto inited;
900 	}
901 
902 	rc = verify_pin(PKCS11_CKU_SO, pin, pin_size,
903 			token->db_main->so_pin_salt,
904 			token->db_main->so_pin_hash);
905 	if (rc) {
906 		unsigned int pin_count = 0;
907 
908 		if (rc != PKCS11_CKR_PIN_INCORRECT)
909 			return rc;
910 
911 		token->db_main->flags |= PKCS11_CKFT_SO_PIN_COUNT_LOW;
912 		token->db_main->so_pin_count++;
913 
914 		pin_count = token->db_main->so_pin_count;
915 		if (pin_count == PKCS11_TOKEN_SO_PIN_COUNT_MAX - 1)
916 			token->db_main->flags |= PKCS11_CKFT_SO_PIN_FINAL_TRY;
917 		if (pin_count == PKCS11_TOKEN_SO_PIN_COUNT_MAX)
918 			token->db_main->flags |= PKCS11_CKFT_SO_PIN_LOCKED;
919 
920 		update_persistent_db(token);
921 
922 		return PKCS11_CKR_PIN_INCORRECT;
923 	}
924 
925 inited:
926 	/* Make sure SO PIN counters are zeroed */
927 	token->db_main->flags &= ~(PKCS11_CKFT_SO_PIN_COUNT_LOW |
928 				   PKCS11_CKFT_SO_PIN_FINAL_TRY |
929 				   PKCS11_CKFT_SO_PIN_LOCKED |
930 				   PKCS11_CKFT_SO_PIN_TO_BE_CHANGED);
931 	token->db_main->so_pin_count = 0;
932 
933 	TEE_MemMove(token->db_main->label, label, PKCS11_TOKEN_LABEL_SIZE);
934 	token->db_main->flags |= PKCS11_CKFT_TOKEN_INITIALIZED;
935 	/* Reset user PIN */
936 	token->db_main->user_pin_salt = 0;
937 	token->db_main->flags &= ~(PKCS11_CKFT_USER_PIN_INITIALIZED |
938 				   PKCS11_CKFT_USER_PIN_COUNT_LOW |
939 				   PKCS11_CKFT_USER_PIN_FINAL_TRY |
940 				   PKCS11_CKFT_USER_PIN_LOCKED |
941 				   PKCS11_CKFT_USER_PIN_TO_BE_CHANGED);
942 
943 	update_persistent_db(token);
944 
945 	/* Remove all persistent objects */
946 	while (!LIST_EMPTY(&token->object_list)) {
947 		obj = LIST_FIRST(&token->object_list);
948 
949 		/* Try twice otherwise panic! */
950 		if (unregister_persistent_object(token, obj->uuid) &&
951 		    unregister_persistent_object(token, obj->uuid))
952 			TEE_Panic(0);
953 
954 		cleanup_persistent_object(obj, token);
955 	}
956 
957 	IMSG("PKCS11 token %"PRIu32": initialized", token_id);
958 
959 	return PKCS11_CKR_OK;
960 }
961 
962 static enum pkcs11_rc set_pin(struct pkcs11_session *session,
963 			      uint8_t *new_pin, size_t new_pin_size,
964 			      enum pkcs11_user_type user_type)
965 {
966 	struct ck_token *token = session->token;
967 	enum pkcs11_rc rc = PKCS11_CKR_OK;
968 	uint32_t flags_clear = 0;
969 	uint32_t flags_set = 0;
970 
971 	if (token->db_main->flags & PKCS11_CKFT_WRITE_PROTECTED)
972 		return PKCS11_CKR_TOKEN_WRITE_PROTECTED;
973 
974 	if (!pkcs11_session_is_read_write(session))
975 		return PKCS11_CKR_SESSION_READ_ONLY;
976 
977 	if (IS_ENABLED(CFG_PKCS11_TA_AUTH_TEE_IDENTITY) &&
978 	    token->db_main->flags & PKCS11_CKFT_PROTECTED_AUTHENTICATION_PATH) {
979 		rc = setup_identity_auth_from_pin(token, user_type, new_pin,
980 						  new_pin_size);
981 		if (rc)
982 			return rc;
983 
984 		goto update_db;
985 	}
986 
987 	if (new_pin_size < PKCS11_TOKEN_PIN_SIZE_MIN ||
988 	    new_pin_size > PKCS11_TOKEN_PIN_SIZE_MAX)
989 		return PKCS11_CKR_PIN_LEN_RANGE;
990 
991 	switch (user_type) {
992 	case PKCS11_CKU_SO:
993 		rc = hash_pin(user_type, new_pin, new_pin_size,
994 			      &token->db_main->so_pin_salt,
995 			      token->db_main->so_pin_hash);
996 		if (rc)
997 			return rc;
998 		token->db_main->so_pin_count = 0;
999 		flags_clear = PKCS11_CKFT_SO_PIN_COUNT_LOW |
1000 			      PKCS11_CKFT_SO_PIN_FINAL_TRY |
1001 			      PKCS11_CKFT_SO_PIN_LOCKED |
1002 			      PKCS11_CKFT_SO_PIN_TO_BE_CHANGED;
1003 		break;
1004 	case PKCS11_CKU_USER:
1005 		rc = hash_pin(user_type, new_pin, new_pin_size,
1006 			      &token->db_main->user_pin_salt,
1007 			      token->db_main->user_pin_hash);
1008 		if (rc)
1009 			return rc;
1010 		token->db_main->user_pin_count = 0;
1011 		flags_clear = PKCS11_CKFT_USER_PIN_COUNT_LOW |
1012 			      PKCS11_CKFT_USER_PIN_FINAL_TRY |
1013 			      PKCS11_CKFT_USER_PIN_LOCKED |
1014 			      PKCS11_CKFT_USER_PIN_TO_BE_CHANGED;
1015 		flags_set = PKCS11_CKFT_USER_PIN_INITIALIZED;
1016 		break;
1017 	default:
1018 		return PKCS11_CKR_FUNCTION_FAILED;
1019 	}
1020 
1021 update_db:
1022 	token->db_main->flags &= ~flags_clear;
1023 	token->db_main->flags |= flags_set;
1024 
1025 	update_persistent_db(token);
1026 
1027 	return PKCS11_CKR_OK;
1028 }
1029 
1030 enum pkcs11_rc entry_ck_init_pin(struct pkcs11_client *client,
1031 				 uint32_t ptypes, TEE_Param *params)
1032 {
1033 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
1034 						TEE_PARAM_TYPE_NONE,
1035 						TEE_PARAM_TYPE_NONE,
1036 						TEE_PARAM_TYPE_NONE);
1037 	struct pkcs11_session *session = NULL;
1038 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1039 	struct serialargs ctrlargs = { };
1040 	TEE_Param *ctrl = params;
1041 	uint32_t pin_size = 0;
1042 	void *pin = NULL;
1043 
1044 	if (!client || ptypes != exp_pt)
1045 		return PKCS11_CKR_ARGUMENTS_BAD;
1046 
1047 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
1048 
1049 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
1050 	if (rc)
1051 		return rc;
1052 
1053 	rc = serialargs_get(&ctrlargs, &pin_size, sizeof(uint32_t));
1054 	if (rc)
1055 		return rc;
1056 
1057 	rc = serialargs_get_ptr(&ctrlargs, &pin, pin_size);
1058 	if (rc)
1059 		return rc;
1060 
1061 	if (serialargs_remaining_bytes(&ctrlargs))
1062 		return PKCS11_CKR_ARGUMENTS_BAD;
1063 
1064 	if (!pkcs11_session_is_so(session))
1065 		return PKCS11_CKR_USER_NOT_LOGGED_IN;
1066 
1067 	assert(session->token->db_main->flags & PKCS11_CKFT_TOKEN_INITIALIZED);
1068 
1069 	IMSG("PKCS11 session %"PRIu32": init PIN", session->handle);
1070 
1071 	return set_pin(session, pin, pin_size, PKCS11_CKU_USER);
1072 }
1073 
1074 static enum pkcs11_rc check_so_pin(struct pkcs11_session *session,
1075 				   uint8_t *pin, size_t pin_size)
1076 {
1077 	struct ck_token *token = session->token;
1078 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1079 
1080 	assert(token->db_main->flags & PKCS11_CKFT_TOKEN_INITIALIZED);
1081 
1082 	if (IS_ENABLED(CFG_PKCS11_TA_AUTH_TEE_IDENTITY) &&
1083 	    token->db_main->flags & PKCS11_CKFT_PROTECTED_AUTHENTICATION_PATH)
1084 		return verify_identity_auth(token, PKCS11_CKU_SO);
1085 
1086 	if (token->db_main->flags & PKCS11_CKFT_SO_PIN_LOCKED)
1087 		return PKCS11_CKR_PIN_LOCKED;
1088 
1089 	rc = verify_pin(PKCS11_CKU_SO, pin, pin_size,
1090 			token->db_main->so_pin_salt,
1091 			token->db_main->so_pin_hash);
1092 	if (rc) {
1093 		unsigned int pin_count = 0;
1094 
1095 		if (rc != PKCS11_CKR_PIN_INCORRECT)
1096 			return rc;
1097 
1098 		token->db_main->flags |= PKCS11_CKFT_SO_PIN_COUNT_LOW;
1099 		token->db_main->so_pin_count++;
1100 
1101 		pin_count = token->db_main->so_pin_count;
1102 		if (pin_count == PKCS11_TOKEN_SO_PIN_COUNT_MAX - 1)
1103 			token->db_main->flags |= PKCS11_CKFT_SO_PIN_FINAL_TRY;
1104 		if (pin_count == PKCS11_TOKEN_SO_PIN_COUNT_MAX)
1105 			token->db_main->flags |= PKCS11_CKFT_SO_PIN_LOCKED;
1106 
1107 		update_persistent_db(token);
1108 
1109 		if (token->db_main->flags & PKCS11_CKFT_SO_PIN_LOCKED)
1110 			return PKCS11_CKR_PIN_LOCKED;
1111 
1112 		return PKCS11_CKR_PIN_INCORRECT;
1113 	}
1114 
1115 	if (token->db_main->so_pin_count) {
1116 		token->db_main->so_pin_count = 0;
1117 
1118 		update_persistent_db(token);
1119 	}
1120 
1121 	if (token->db_main->flags & (PKCS11_CKFT_SO_PIN_COUNT_LOW |
1122 				     PKCS11_CKFT_SO_PIN_FINAL_TRY)) {
1123 		token->db_main->flags &= ~(PKCS11_CKFT_SO_PIN_COUNT_LOW |
1124 					   PKCS11_CKFT_SO_PIN_FINAL_TRY);
1125 
1126 		update_persistent_db(token);
1127 	}
1128 
1129 	return PKCS11_CKR_OK;
1130 }
1131 
1132 static enum pkcs11_rc check_user_pin(struct pkcs11_session *session,
1133 				     uint8_t *pin, size_t pin_size)
1134 {
1135 	struct ck_token *token = session->token;
1136 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1137 
1138 	if (IS_ENABLED(CFG_PKCS11_TA_AUTH_TEE_IDENTITY) &&
1139 	    token->db_main->flags & PKCS11_CKFT_PROTECTED_AUTHENTICATION_PATH)
1140 		return verify_identity_auth(token, PKCS11_CKU_USER);
1141 
1142 	if (!token->db_main->user_pin_salt)
1143 		return PKCS11_CKR_USER_PIN_NOT_INITIALIZED;
1144 
1145 	if (token->db_main->flags & PKCS11_CKFT_USER_PIN_LOCKED)
1146 		return PKCS11_CKR_PIN_LOCKED;
1147 
1148 	rc = verify_pin(PKCS11_CKU_USER, pin, pin_size,
1149 			token->db_main->user_pin_salt,
1150 			token->db_main->user_pin_hash);
1151 	if (rc) {
1152 		unsigned int pin_count = 0;
1153 
1154 		if (rc != PKCS11_CKR_PIN_INCORRECT)
1155 			return rc;
1156 
1157 		token->db_main->flags |= PKCS11_CKFT_USER_PIN_COUNT_LOW;
1158 		token->db_main->user_pin_count++;
1159 
1160 		pin_count = token->db_main->user_pin_count;
1161 		if (pin_count == PKCS11_TOKEN_USER_PIN_COUNT_MAX - 1)
1162 			token->db_main->flags |= PKCS11_CKFT_USER_PIN_FINAL_TRY;
1163 		if (pin_count == PKCS11_TOKEN_USER_PIN_COUNT_MAX)
1164 			token->db_main->flags |= PKCS11_CKFT_USER_PIN_LOCKED;
1165 
1166 		update_persistent_db(token);
1167 
1168 		if (token->db_main->flags & PKCS11_CKFT_USER_PIN_LOCKED)
1169 			return PKCS11_CKR_PIN_LOCKED;
1170 
1171 		return PKCS11_CKR_PIN_INCORRECT;
1172 	}
1173 
1174 	if (token->db_main->user_pin_count) {
1175 		token->db_main->user_pin_count = 0;
1176 
1177 		update_persistent_db(token);
1178 	}
1179 
1180 	if (token->db_main->flags & (PKCS11_CKFT_USER_PIN_COUNT_LOW |
1181 				     PKCS11_CKFT_USER_PIN_FINAL_TRY)) {
1182 		token->db_main->flags &= ~(PKCS11_CKFT_USER_PIN_COUNT_LOW |
1183 					   PKCS11_CKFT_USER_PIN_FINAL_TRY);
1184 
1185 		update_persistent_db(token);
1186 	}
1187 
1188 	return PKCS11_CKR_OK;
1189 }
1190 
1191 enum pkcs11_rc entry_ck_set_pin(struct pkcs11_client *client,
1192 				uint32_t ptypes, TEE_Param *params)
1193 {
1194 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
1195 						TEE_PARAM_TYPE_NONE,
1196 						TEE_PARAM_TYPE_NONE,
1197 						TEE_PARAM_TYPE_NONE);
1198 	struct pkcs11_session *session = NULL;
1199 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1200 	struct serialargs ctrlargs = { };
1201 	uint32_t old_pin_size = 0;
1202 	TEE_Param *ctrl = params;
1203 	uint32_t pin_size = 0;
1204 	void *old_pin = NULL;
1205 	void *pin = NULL;
1206 
1207 	if (!client || ptypes != exp_pt)
1208 		return PKCS11_CKR_ARGUMENTS_BAD;
1209 
1210 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
1211 
1212 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
1213 	if (rc)
1214 		return rc;
1215 
1216 	rc = serialargs_get(&ctrlargs, &old_pin_size, sizeof(uint32_t));
1217 	if (rc)
1218 		return rc;
1219 
1220 	rc = serialargs_get(&ctrlargs, &pin_size, sizeof(uint32_t));
1221 	if (rc)
1222 		return rc;
1223 
1224 	rc = serialargs_get_ptr(&ctrlargs, &old_pin, old_pin_size);
1225 	if (rc)
1226 		return rc;
1227 
1228 	rc = serialargs_get_ptr(&ctrlargs, &pin, pin_size);
1229 	if (rc)
1230 		return rc;
1231 
1232 	if (serialargs_remaining_bytes(&ctrlargs))
1233 		return PKCS11_CKR_ARGUMENTS_BAD;
1234 
1235 	if (!pkcs11_session_is_read_write(session))
1236 		return PKCS11_CKR_SESSION_READ_ONLY;
1237 
1238 	if (pkcs11_session_is_so(session)) {
1239 		if (!(session->token->db_main->flags &
1240 		      PKCS11_CKFT_TOKEN_INITIALIZED))
1241 			return PKCS11_CKR_GENERAL_ERROR;
1242 
1243 		rc = check_so_pin(session, old_pin, old_pin_size);
1244 		if (rc)
1245 			return rc;
1246 
1247 		IMSG("PKCS11 session %"PRIu32": set PIN", session->handle);
1248 
1249 		return set_pin(session, pin, pin_size, PKCS11_CKU_SO);
1250 	}
1251 
1252 	if (!(session->token->db_main->flags &
1253 	      PKCS11_CKFT_USER_PIN_INITIALIZED))
1254 		return PKCS11_CKR_GENERAL_ERROR;
1255 
1256 	rc = check_user_pin(session, old_pin, old_pin_size);
1257 	if (rc)
1258 		return rc;
1259 
1260 	IMSG("PKCS11 session %"PRIu32": set PIN", session->handle);
1261 
1262 	return set_pin(session, pin, pin_size, PKCS11_CKU_USER);
1263 }
1264 
1265 static void session_login_user(struct pkcs11_session *session)
1266 {
1267 	struct pkcs11_client *client = session->client;
1268 	struct pkcs11_session *sess = NULL;
1269 
1270 	TAILQ_FOREACH(sess, &client->session_list, link) {
1271 		if (sess->token != session->token)
1272 			continue;
1273 
1274 		if (pkcs11_session_is_read_write(sess))
1275 			sess->state = PKCS11_CKS_RW_USER_FUNCTIONS;
1276 		else
1277 			sess->state = PKCS11_CKS_RO_USER_FUNCTIONS;
1278 	}
1279 }
1280 
1281 static void session_login_so(struct pkcs11_session *session)
1282 {
1283 	struct pkcs11_client *client = session->client;
1284 	struct pkcs11_session *sess = NULL;
1285 
1286 	TAILQ_FOREACH(sess, &client->session_list, link) {
1287 		if (sess->token != session->token)
1288 			continue;
1289 
1290 		if (pkcs11_session_is_read_write(sess))
1291 			sess->state = PKCS11_CKS_RW_SO_FUNCTIONS;
1292 		else
1293 			TEE_Panic(0);
1294 	}
1295 }
1296 
1297 static void session_logout(struct pkcs11_session *session)
1298 {
1299 	struct pkcs11_client *client = session->client;
1300 	struct pkcs11_session *sess = NULL;
1301 
1302 	TAILQ_FOREACH(sess, &client->session_list, link) {
1303 		struct pkcs11_object *obj = NULL;
1304 		struct pkcs11_object *tobj = NULL;
1305 		uint32_t handle = 0;
1306 
1307 		if (sess->token != session->token)
1308 			continue;
1309 
1310 		release_active_processing(session);
1311 
1312 		/* Destroy private session objects */
1313 		LIST_FOREACH_SAFE(obj, &sess->object_list, link, tobj) {
1314 			if (object_is_private(obj->attributes))
1315 				destroy_object(sess, obj, true);
1316 		}
1317 
1318 		/*
1319 		 * Remove handle of token private objects from
1320 		 * sessions object_handle_db
1321 		 */
1322 		LIST_FOREACH(obj, &session->token->object_list, link) {
1323 			handle = pkcs11_object2handle(obj, session);
1324 
1325 			if (handle && object_is_private(obj->attributes))
1326 				handle_put(get_object_handle_db(sess), handle);
1327 		}
1328 
1329 		release_session_find_obj_context(session);
1330 
1331 		if (pkcs11_session_is_read_write(sess))
1332 			sess->state = PKCS11_CKS_RW_PUBLIC_SESSION;
1333 		else
1334 			sess->state = PKCS11_CKS_RO_PUBLIC_SESSION;
1335 	}
1336 }
1337 
1338 enum pkcs11_rc entry_ck_login(struct pkcs11_client *client,
1339 			      uint32_t ptypes, TEE_Param *params)
1340 {
1341 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
1342 						TEE_PARAM_TYPE_NONE,
1343 						TEE_PARAM_TYPE_NONE,
1344 						TEE_PARAM_TYPE_NONE);
1345 	struct pkcs11_session *session = NULL;
1346 	struct pkcs11_session *sess = NULL;
1347 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1348 	struct serialargs ctrlargs = { };
1349 	TEE_Param *ctrl = params;
1350 	uint32_t user_type = 0;
1351 	uint32_t pin_size = 0;
1352 	void *pin = NULL;
1353 
1354 	if (!client || ptypes != exp_pt)
1355 		return PKCS11_CKR_ARGUMENTS_BAD;
1356 
1357 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
1358 
1359 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
1360 	if (rc)
1361 		return rc;
1362 
1363 	rc = serialargs_get(&ctrlargs, &user_type, sizeof(uint32_t));
1364 	if (rc)
1365 		return rc;
1366 
1367 	rc = serialargs_get(&ctrlargs, &pin_size, sizeof(uint32_t));
1368 	if (rc)
1369 		return rc;
1370 
1371 	rc = serialargs_get_ptr(&ctrlargs, &pin, pin_size);
1372 	if (rc)
1373 		return rc;
1374 
1375 	if (serialargs_remaining_bytes(&ctrlargs))
1376 		return PKCS11_CKR_ARGUMENTS_BAD;
1377 
1378 	switch (user_type) {
1379 	case PKCS11_CKU_SO:
1380 		if (pkcs11_session_is_so(session))
1381 			return PKCS11_CKR_USER_ALREADY_LOGGED_IN;
1382 
1383 		if (pkcs11_session_is_user(session))
1384 			return PKCS11_CKR_USER_ANOTHER_ALREADY_LOGGED_IN;
1385 
1386 		TAILQ_FOREACH(sess, &client->session_list, link)
1387 			if (sess->token == session->token &&
1388 			    !pkcs11_session_is_read_write(sess))
1389 				return PKCS11_CKR_SESSION_READ_ONLY_EXISTS;
1390 
1391 		/*
1392 		 * This is the point where we could check if another client
1393 		 * has another user or SO logged in.
1394 		 *
1395 		 * The spec says:
1396 		 * CKR_USER_TOO_MANY_TYPES: An attempt was made to have
1397 		 * more distinct users simultaneously logged into the token
1398 		 * than the token and/or library permits. For example, if
1399 		 * some application has an open SO session, and another
1400 		 * application attempts to log the normal user into a
1401 		 * session, the attempt may return this error. It is not
1402 		 * required to, however. Only if the simultaneous distinct
1403 		 * users cannot be supported does C_Login have to return
1404 		 * this value. Note that this error code generalizes to
1405 		 * true multi-user tokens.
1406 		 *
1407 		 * So it's permitted to have another user or SO logged in
1408 		 * from another client.
1409 		 */
1410 
1411 		rc = check_so_pin(session, pin, pin_size);
1412 		if (!rc)
1413 			session_login_so(session);
1414 
1415 		break;
1416 
1417 	case PKCS11_CKU_USER:
1418 		if (pkcs11_session_is_so(session))
1419 			return PKCS11_CKR_USER_ANOTHER_ALREADY_LOGGED_IN;
1420 
1421 		if (pkcs11_session_is_user(session))
1422 			return PKCS11_CKR_USER_ALREADY_LOGGED_IN;
1423 
1424 		/*
1425 		 * This is the point where we could check if another client
1426 		 * has another user or SO logged in.
1427 		 * See comment on CKR_USER_TOO_MANY_TYPES above.
1428 		 */
1429 
1430 		rc = check_user_pin(session, pin, pin_size);
1431 		if (!rc)
1432 			session_login_user(session);
1433 
1434 		break;
1435 
1436 	case PKCS11_CKU_CONTEXT_SPECIFIC:
1437 		return PKCS11_CKR_OPERATION_NOT_INITIALIZED;
1438 
1439 	default:
1440 		return PKCS11_CKR_USER_TYPE_INVALID;
1441 	}
1442 
1443 	if (!rc)
1444 		IMSG("PKCS11 session %"PRIu32": login", session->handle);
1445 
1446 	return rc;
1447 }
1448 
1449 enum pkcs11_rc entry_ck_logout(struct pkcs11_client *client,
1450 			       uint32_t ptypes, TEE_Param *params)
1451 {
1452 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
1453 						TEE_PARAM_TYPE_NONE,
1454 						TEE_PARAM_TYPE_NONE,
1455 						TEE_PARAM_TYPE_NONE);
1456 	struct pkcs11_session *session = NULL;
1457 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1458 	struct serialargs ctrlargs = { };
1459 	TEE_Param *ctrl = params;
1460 
1461 	if (!client || ptypes != exp_pt)
1462 		return PKCS11_CKR_ARGUMENTS_BAD;
1463 
1464 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
1465 
1466 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
1467 	if (rc)
1468 		return rc;
1469 
1470 	if (serialargs_remaining_bytes(&ctrlargs))
1471 		return PKCS11_CKR_ARGUMENTS_BAD;
1472 
1473 	if (pkcs11_session_is_public(session))
1474 		return PKCS11_CKR_USER_NOT_LOGGED_IN;
1475 
1476 	session_logout(session);
1477 
1478 	IMSG("PKCS11 session %"PRIu32": logout", session->handle);
1479 
1480 	return PKCS11_CKR_OK;
1481 }
1482 
1483 static TEE_Result seed_rng_pool(void *seed, size_t length)
1484 {
1485 	static const TEE_UUID system_uuid = PTA_SYSTEM_UUID;
1486 	uint32_t param_types = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INPUT,
1487 					       TEE_PARAM_TYPE_NONE,
1488 					       TEE_PARAM_TYPE_NONE,
1489 					       TEE_PARAM_TYPE_NONE);
1490 	TEE_Param params[TEE_NUM_PARAMS] = { };
1491 	TEE_TASessionHandle sess = TEE_HANDLE_NULL;
1492 	TEE_Result res = TEE_ERROR_GENERIC;
1493 	uint32_t ret_orig = 0;
1494 
1495 	params[0].memref.buffer = seed;
1496 	params[0].memref.size = (uint32_t)length;
1497 
1498 	res = TEE_OpenTASession(&system_uuid, TEE_TIMEOUT_INFINITE, 0, NULL,
1499 				&sess, &ret_orig);
1500 	if (res != TEE_SUCCESS) {
1501 		EMSG("Can't open session to system PTA");
1502 		return res;
1503 	}
1504 
1505 	res = TEE_InvokeTACommand(sess, TEE_TIMEOUT_INFINITE,
1506 				  PTA_SYSTEM_ADD_RNG_ENTROPY,
1507 				  param_types, params, &ret_orig);
1508 	if (res != TEE_SUCCESS)
1509 		EMSG("Can't invoke system PTA");
1510 
1511 	TEE_CloseTASession(sess);
1512 	return res;
1513 }
1514 
1515 enum pkcs11_rc entry_ck_seed_random(struct pkcs11_client *client,
1516 				    uint32_t ptypes, TEE_Param *params)
1517 {
1518 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
1519 						TEE_PARAM_TYPE_MEMREF_INPUT,
1520 						TEE_PARAM_TYPE_NONE,
1521 						TEE_PARAM_TYPE_NONE);
1522 	TEE_Param *ctrl = params;
1523 	TEE_Param *in = params + 1;
1524 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1525 	struct serialargs ctrlargs = { };
1526 	struct pkcs11_session *session = NULL;
1527 	TEE_Result res = TEE_SUCCESS;
1528 
1529 	if (!client || ptypes != exp_pt)
1530 		return PKCS11_CKR_ARGUMENTS_BAD;
1531 
1532 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
1533 
1534 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
1535 	if (rc)
1536 		return rc;
1537 
1538 	if (serialargs_remaining_bytes(&ctrlargs))
1539 		return PKCS11_CKR_ARGUMENTS_BAD;
1540 
1541 	if (in->memref.size && !in->memref.buffer)
1542 		return PKCS11_CKR_ARGUMENTS_BAD;
1543 
1544 	if (!in->memref.size)
1545 		return PKCS11_CKR_OK;
1546 
1547 	res = seed_rng_pool(in->memref.buffer, in->memref.size);
1548 	if (res != TEE_SUCCESS)
1549 		return PKCS11_CKR_FUNCTION_FAILED;
1550 
1551 	DMSG("PKCS11 session %"PRIu32": seed random", session->handle);
1552 
1553 	return PKCS11_CKR_OK;
1554 }
1555 
1556 enum pkcs11_rc entry_ck_generate_random(struct pkcs11_client *client,
1557 					uint32_t ptypes, TEE_Param *params)
1558 {
1559 	const uint32_t exp_pt = TEE_PARAM_TYPES(TEE_PARAM_TYPE_MEMREF_INOUT,
1560 						TEE_PARAM_TYPE_NONE,
1561 						TEE_PARAM_TYPE_MEMREF_OUTPUT,
1562 						TEE_PARAM_TYPE_NONE);
1563 	TEE_Param *ctrl = params;
1564 	TEE_Param *out = params + 2;
1565 	enum pkcs11_rc rc = PKCS11_CKR_OK;
1566 	struct serialargs ctrlargs = { };
1567 	struct pkcs11_session *session = NULL;
1568 	void *buffer = NULL;
1569 	size_t buffer_size = 0;
1570 	uint8_t *data = NULL;
1571 	size_t left = 0;
1572 
1573 	if (!client || ptypes != exp_pt)
1574 		return PKCS11_CKR_ARGUMENTS_BAD;
1575 
1576 	serialargs_init(&ctrlargs, ctrl->memref.buffer, ctrl->memref.size);
1577 
1578 	rc = serialargs_get_session_from_handle(&ctrlargs, client, &session);
1579 	if (rc)
1580 		return rc;
1581 
1582 	if (serialargs_remaining_bytes(&ctrlargs))
1583 		return PKCS11_CKR_ARGUMENTS_BAD;
1584 
1585 	if (out->memref.size && !out->memref.buffer)
1586 		return PKCS11_CKR_ARGUMENTS_BAD;
1587 
1588 	if (!out->memref.size)
1589 		return PKCS11_CKR_OK;
1590 
1591 	buffer_size = MIN(out->memref.size, RNG_CHUNK_SIZE);
1592 	buffer = TEE_Malloc(buffer_size, TEE_MALLOC_FILL_ZERO);
1593 	if (!buffer)
1594 		return PKCS11_CKR_DEVICE_MEMORY;
1595 
1596 	data = out->memref.buffer;
1597 	left = out->memref.size;
1598 
1599 	while (left) {
1600 		size_t count = MIN(left, buffer_size);
1601 
1602 		TEE_GenerateRandom(buffer, count);
1603 		TEE_MemMove(data, buffer, count);
1604 
1605 		data += count;
1606 		left -= count;
1607 	}
1608 
1609 	DMSG("PKCS11 session %"PRIu32": generate random", session->handle);
1610 
1611 	TEE_Free(buffer);
1612 
1613 	return PKCS11_CKR_OK;
1614 }
1615