1 /* SPDX-License-Identifier: LGPL-2.1-or-later */
3 #include "cryptenroll-list.h"
4 #include "cryptenroll.h"
5 #include "format-table.h"
6 #include "parse-util.h"
8 int list_enrolled(struct crypt_device
*cd
) {
10 struct keyslot_metadata
{
13 } *keyslot_metadata
= NULL
;
14 _cleanup_(table_unrefp
) Table
*t
= NULL
;
15 size_t n_keyslot_metadata
= 0;
21 /* First step, find out all currently used slots */
22 assert_se((slot_max
= crypt_keyslot_max(CRYPT_LUKS2
)) > 0);
23 for (int slot
= 0; slot
< slot_max
; slot
++) {
24 crypt_keyslot_info status
;
26 status
= crypt_keyslot_status(cd
, slot
);
27 if (!IN_SET(status
, CRYPT_SLOT_ACTIVE
, CRYPT_SLOT_ACTIVE_LAST
))
30 if (!GREEDY_REALLOC(keyslot_metadata
, n_keyslot_metadata
+1))
33 keyslot_metadata
[n_keyslot_metadata
++] = (struct keyslot_metadata
) {
38 /* Second step, enumerate through all tokens, and update the slot table, indicating what kind of
39 * token they are assigned to */
40 for (int token
= 0; token
< sym_crypt_token_max(CRYPT_LUKS2
); token
++) {
41 _cleanup_(json_variant_unrefp
) JsonVariant
*v
= NULL
;
46 r
= cryptsetup_get_token_as_json(cd
, token
, NULL
, &v
);
47 if (IN_SET(r
, -ENOENT
, -EINVAL
))
50 log_warning_errno(r
, "Failed to read JSON token data off disk, ignoring: %m");
54 w
= json_variant_by_key(v
, "type");
55 if (!w
|| !json_variant_is_string(w
)) {
56 log_warning("Token JSON data lacks type field, ignoring.");
60 et
= luks2_token_type_from_string(json_variant_string(w
));
64 type
= enroll_type_to_string(et
);
66 w
= json_variant_by_key(v
, "keyslots");
67 if (!w
|| !json_variant_is_array(w
)) {
68 log_warning("Token JSON data lacks keyslots field, ignoring.");
72 JSON_VARIANT_ARRAY_FOREACH(z
, w
) {
75 if (!json_variant_is_string(z
)) {
76 log_warning("Token JSON data's keyslot field is not an array of strings, ignoring.");
80 r
= safe_atou(json_variant_string(z
), &u
);
82 log_warning_errno(r
, "Token JSON data's keyslot filed is not an integer formatted as string, ignoring.");
86 for (size_t i
= 0; i
< n_keyslot_metadata
; i
++) {
87 if ((unsigned) keyslot_metadata
[i
].slot
!= u
)
90 if (keyslot_metadata
[i
].type
) /* Slot claimed multiple times? */
91 keyslot_metadata
[i
].type
= POINTER_MAX
;
93 keyslot_metadata
[i
].type
= type
;
98 /* Finally, create a table out of it all */
99 t
= table_new("slot", "type");
103 assert_se(cell
= table_get_cell(t
, 0, 0));
104 (void) table_set_align_percent(t
, cell
, 100);
106 for (size_t i
= 0; i
< n_keyslot_metadata
; i
++) {
109 TABLE_INT
, keyslot_metadata
[i
].slot
,
110 TABLE_STRING
, keyslot_metadata
[i
].type
== POINTER_MAX
? "conflict" :
111 keyslot_metadata
[i
].type
?: "password");
113 return table_log_add_error(r
);
116 if (table_get_rows(t
) <= 1) {
117 log_info("No slots found.");
121 r
= table_print(t
, stdout
);
123 return log_error_errno(r
, "Failed to show slot table: %m");