From 016c355cf798415070c64435fe6b1eeff820ea29f099101e9862d5992722cd83 Mon Sep 17 00:00:00 2001 From: Gary Ching-Pang Lin Date: Thu, 17 Sep 2020 06:11:04 +0000 Subject: [PATCH] Accepting request 835083 from home:gary_lin:branches:Base:System add options for CA and kernel keyring checks (bsc#1173115) OBS-URL: https://build.opensuse.org/request/show/835083 OBS-URL: https://build.opensuse.org/package/show/Base:System/mokutil?expand=0&rev=45 --- ...bsc1173115-add-ca-and-keyring-checks.patch | 1159 +++++++++++++++++ mokutil-remove-libkeyutils-check.patch | 46 + mokutil-support-revoke-builtin-cert.patch | 58 +- mokutil.changes | 10 + mokutil.spec | 7 + 5 files changed, 1251 insertions(+), 29 deletions(-) create mode 100644 mokutil-bsc1173115-add-ca-and-keyring-checks.patch create mode 100644 mokutil-remove-libkeyutils-check.patch diff --git a/mokutil-bsc1173115-add-ca-and-keyring-checks.patch b/mokutil-bsc1173115-add-ca-and-keyring-checks.patch new file mode 100644 index 0000000..ec6323a --- /dev/null +++ b/mokutil-bsc1173115-add-ca-and-keyring-checks.patch @@ -0,0 +1,1159 @@ +From edbb90e7b9dddcb6561af244a65d10d6a22e6bae Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Thu, 27 Aug 2020 11:31:08 +0800 +Subject: [PATCH 01/13] efi_x509: add the function to check immediate CA + +Add a new function, is_immediate_ca(), to check whether the given CA +cert is the immediate CA of the cert. + +Signed-off-by: Gary Lin +(cherry picked from commit 643bb8dacb221979354dab814fc2d41e94a02d67) +--- + src/mokutil.c | 73 +++++++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 73 insertions(+) + +diff --git a/src/mokutil.c b/src/mokutil.c +index e2d567d..3735167 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -1032,6 +1032,79 @@ is_valid_cert (void *cert, uint32_t cert_size) + return 1; + } + ++/** ++ * Check whether the given CA cert is the immediate CA of the given cert ++ **/ ++static int ++is_immediate_ca (const uint8_t *cert, const uint32_t cert_size, ++ const uint8_t *ca_cert, const uint32_t ca_cert_size) ++{ ++ X509 *X509cert = NULL; ++ X509 *X509ca = NULL; ++ X509_STORE *cert_store = NULL; ++ X509_STORE_CTX *cert_ctx = NULL; ++ int ret = 0; ++ ++ if (cert == NULL || ca_cert == NULL) ++ return 0; ++ ++ if (EVP_add_digest (EVP_md5 ()) == 0) ++ return 0; ++ if (EVP_add_digest (EVP_sha1 ()) == 0) ++ return 0; ++ if (EVP_add_digest (EVP_sha256 ()) == 0) ++ return 0; ++ ++ X509cert = d2i_X509 (NULL, &cert, cert_size); ++ if (X509cert == NULL) ++ return 0; ++ ++ X509ca = d2i_X509 (NULL, &ca_cert, ca_cert_size); ++ if (X509ca == NULL) ++ return 0; ++ ++ cert_store = X509_STORE_new (); ++ if (cert_store == NULL) ++ goto err; ++ ++ if (X509_STORE_add_cert (cert_store, X509ca) == 0) ++ goto err; ++ ++ /* Follow edk2 CryptoPkg to allow partial certificate chains and ++ * disable time checks */ ++ X509_STORE_set_flags (cert_store, ++ X509_V_FLAG_PARTIAL_CHAIN | X509_V_FLAG_NO_CHECK_TIME); ++ ++ cert_ctx = X509_STORE_CTX_new (); ++ if (cert_ctx == NULL) ++ goto err; ++ ++ if (X509_STORE_CTX_init (cert_ctx, cert_store, X509cert, NULL) == 0) ++ goto err; ++ ++ /* Verify the cert */ ++ ret = X509_verify_cert (cert_ctx); ++ /* Treat the exceptional error as FALSE */ ++ if (ret < 0) ++ ret = 0; ++ X509_STORE_CTX_cleanup (cert_ctx); ++ ++err: ++ if (X509cert) ++ X509_free (X509cert); ++ ++ if (X509ca) ++ X509_free (X509ca); ++ ++ if (cert_store) ++ X509_STORE_free (cert_store); ++ ++ if (cert_store) ++ X509_STORE_CTX_free (cert_ctx); ++ ++ return ret; ++} ++ + static int + is_duplicate (const efi_guid_t *type, const void *data, const uint32_t data_size, + const efi_guid_t *vendor, const char *db_name) +-- +2.28.0 + + +From db7216b3a758ba62f02154b79a77c878fd0fd85e Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Thu, 27 Aug 2020 14:11:56 +0800 +Subject: [PATCH 02/13] mokutil: do the CA check + +Check whether th CA cert is already enrolled in the key database before +enrolling the key. + +The check can be disabled with "--ignore-ca-check". + +Signed-off-by: Gary Lin +(cherry picked from commit ff20a53a111fe3e027da7250175b7ef09ce3b1da) +--- + src/mokutil.c | 88 +++++++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 88 insertions(+) + +diff --git a/src/mokutil.c b/src/mokutil.c +index 3735167..4ac6619 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -95,6 +95,7 @@ typedef uint8_t efi_bool_t; + typedef wchar_t efi_char16_t; /* UNICODE character */ + + static int use_simple_hash; ++static int force_ca_check; + + typedef enum { + DELETE_MOK = 0, +@@ -182,6 +183,7 @@ print_help () + printf (" --root-pw\t\t\t\tUse the root password\n"); + printf (" --simple-hash\t\t\t\tUse the old password hash method\n"); + printf (" --mokx\t\t\t\tManipulate the MOK blacklist\n"); ++ printf (" --ignore-ca-check\t\t\tDon't check CA of the given certificate\n"); + } + + static int +@@ -1237,6 +1239,70 @@ in_pending_request (const efi_guid_t *type, void *data, uint32_t data_size, + return ret; + } + ++static int ++is_ca_in_db (const void *cert, const uint32_t cert_size, ++ const efi_guid_t *vendor, const char *db_name) ++{ ++ uint8_t *var_data; ++ size_t var_data_size; ++ uint32_t attributes; ++ uint32_t node_num; ++ MokListNode *list; ++ int ret = 0; ++ ++ if (!cert || cert_size == 0 || !vendor || !db_name) ++ return 0; ++ ++ ret = efi_get_variable (*vendor, db_name, &var_data, &var_data_size, ++ &attributes); ++ if (ret < 0) ++ return 0; ++ ++ list = build_mok_list (var_data, var_data_size, &node_num); ++ if (list == NULL) { ++ goto done; ++ } ++ ++ for (unsigned int i = 0; i < node_num; i++) { ++ efi_guid_t sigtype = list[i].header->SignatureType; ++ if (efi_guid_cmp (&sigtype, &efi_guid_x509_cert) != 0) ++ continue; ++ ++ if (is_immediate_ca (cert, cert_size, list[i].mok, ++ list[i].mok_size)) { ++ ret = 1; ++ break; ++ } ++ } ++ ++done: ++ if (list) ++ free (list); ++ free (var_data); ++ ++ return ret; ++} ++ ++/* Check whether the CA cert is already enrolled */ ++static int ++is_ca_enrolled (void *mok, uint32_t mok_size, MokRequest req) ++{ ++ switch (req) { ++ case ENROLL_MOK: ++ if (is_ca_in_db (mok, mok_size, &efi_guid_shim, "MokListRT")) ++ return 1; ++ break; ++ case ENROLL_BLACKLIST: ++ if (is_ca_in_db (mok, mok_size, &efi_guid_shim, "MokListXRT")) ++ return 1; ++ break; ++ default: ++ return 0; ++ } ++ ++ return 0; ++} ++ + static void + print_skip_message (const char *filename, void *mok, uint32_t mok_size, + MokRequest req) +@@ -1394,6 +1460,13 @@ issue_mok_request (char **files, uint32_t total, MokRequest req, + goto error; + } + ++ /* Check whether CA is already enrolled */ ++ if (force_ca_check && is_ca_enrolled (ptr, sizes[i], req)) { ++ fprintf (stderr, "CA of %s is already enrolled\n", ++ files[i]); ++ goto error; ++ } ++ + if (is_valid_request (&efi_guid_x509_cert, ptr, sizes[i], req)) { + ptr += sizes[i]; + real_size += sizes[i] + sizeof(EFI_SIGNATURE_LIST) + sizeof(efi_guid_t); +@@ -2041,6 +2114,17 @@ test_key (MokRequest req, const char *key_file) + goto error; + } + ++ if (!is_valid_cert (key, read_size)) { ++ fprintf (stderr, "Not a valid x509 certificate\n"); ++ goto error; ++ } ++ ++ if (force_ca_check && is_ca_enrolled (key, read_size, req)) { ++ fprintf (stderr, "CA of %s is already enrolled\n", ++ key_file); ++ goto error; ++ } ++ + if (is_valid_request (&efi_guid_x509_cert, key, read_size, req)) { + printf ("%s is not enrolled\n", key_file); + ret = 0; +@@ -2215,6 +2299,7 @@ main (int argc, char *argv[]) + int ret = -1; + + use_simple_hash = 0; ++ force_ca_check = 1; + + if (!efi_variables_supported ()) { + fprintf (stderr, "EFI variables are not supported on this system\n"); +@@ -2255,6 +2340,7 @@ main (int argc, char *argv[]) + {"db", no_argument, 0, 0 }, + {"dbx", no_argument, 0, 0 }, + {"timeout", required_argument, 0, 0 }, ++ {"ignore-ca-check", no_argument, 0, 0 }, + {0, 0, 0, 0} + }; + +@@ -2341,6 +2427,8 @@ main (int argc, char *argv[]) + } else if (strcmp (option, "timeout") == 0) { + command |= TIMEOUT; + timeout = strdup (optarg); ++ } else if (strcmp (option, "ignore-ca-check") == 0) { ++ force_ca_check = 0; + } + + break; +-- +2.28.0 + + +From 3bfcf1db9ab1ff2bd4a2ddd2649c03337f823a2d Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Thu, 27 Aug 2020 14:18:29 +0800 +Subject: [PATCH 03/13] mokutil: close file in the error path + +We should close the file descriptor when encountering an error in +issue_mok_request(); + +Signed-off-by: Gary Lin +(cherry picked from commit 0a0813d6f7dfa73f7947566e7fad2d42e016f30a) +--- + src/mokutil.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/src/mokutil.c b/src/mokutil.c +index 4ac6619..760b54a 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -1452,11 +1452,13 @@ issue_mok_request (char **files, uint32_t total, MokRequest req, + read_size = read (fd, ptr, sizes[i]); + if (read_size < 0 || read_size != (int64_t)sizes[i]) { + fprintf (stderr, "Failed to read %s\n", files[i]); ++ close (fd); + goto error; + } + if (!is_valid_cert (ptr, read_size)) { + fprintf (stderr, "Abort!!! %s is not a valid x509 certificate in DER format\n", + files[i]); ++ close (fd); + goto error; + } + +@@ -1464,6 +1466,7 @@ issue_mok_request (char **files, uint32_t total, MokRequest req, + if (force_ca_check && is_ca_enrolled (ptr, sizes[i], req)) { + fprintf (stderr, "CA of %s is already enrolled\n", + files[i]); ++ close (fd); + goto error; + } + +-- +2.28.0 + + +From 77be7a26815233e798f6ab61cbbd8a1cd4a89817 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Thu, 27 Aug 2020 14:22:52 +0800 +Subject: [PATCH 04/13] make CA check non-fatal + +(cherry picked from commit 50098834780ee6d5dd0cfd3073d504030cc25037) +--- + src/mokutil.c | 5 ++--- + 1 file changed, 2 insertions(+), 3 deletions(-) + +diff --git a/src/mokutil.c b/src/mokutil.c +index 760b54a..f4f21f8 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -1464,10 +1464,9 @@ issue_mok_request (char **files, uint32_t total, MokRequest req, + + /* Check whether CA is already enrolled */ + if (force_ca_check && is_ca_enrolled (ptr, sizes[i], req)) { +- fprintf (stderr, "CA of %s is already enrolled\n", +- files[i]); ++ printf ("CA enrolled. Skip %s\n", files[i]); + close (fd); +- goto error; ++ continue; + } + + if (is_valid_request (&efi_guid_x509_cert, ptr, sizes[i], req)) { +-- +2.28.0 + + +From e4a28a587f39912c65e3f74f0ff9766158ef9dff Mon Sep 17 00:00:00 2001 +From: Sandy <39258624+sandy-lcq@users.noreply.github.com> +Date: Fri, 13 Dec 2019 10:38:28 +0800 +Subject: [PATCH 05/13] mokutil.c: fix typo enrollement -> enrollment + +Signed-off-by: Changqing Li +(cherry picked from commit e37eeef4866f5f3bbeaef3fe1d1360ebac76bdc5) +--- + src/mokutil.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/src/mokutil.c b/src/mokutil.c +index f4f21f8..ee95e20 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -1323,7 +1323,7 @@ print_skip_message (const char *filename, void *mok, uint32_t mok_size, + printf ("SKIP: %s is already enrolled\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokNew")) +- printf ("SKIP: %s is already in the enrollement request\n", filename); ++ printf ("SKIP: %s is already in the enrollment request\n", filename); + break; + case DELETE_MOK: + if (!is_duplicate (&efi_guid_x509_cert, mok, mok_size, +-- +2.28.0 + + +From f18969c91a44fee03a1ab8da336973f36ef7e5e9 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Fri, 28 Aug 2020 11:53:24 +0800 +Subject: [PATCH 06/13] mokutil: check the blocklists before enrolling a key + +Check "dbx" and "MokListXRT" when enrolling a key. + +Signed-off-by: Gary Lin +(cherry picked from commit 8de04a4dd566376316432bd60c3b0ab2686797a4) +--- + src/mokutil.c | 40 ++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 40 insertions(+) + +diff --git a/src/mokutil.c b/src/mokutil.c +index ee95e20..834228a 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -1173,6 +1173,10 @@ is_valid_request (const efi_guid_t *type, void *mok, uint32_t mok_size, + is_duplicate (type, mok, mok_size, &efi_guid_shim, "MokNew")) { + return 0; + } ++ /* Also check the blocklists */ ++ if (is_duplicate (type, mok, mok_size, &efi_guid_security, "dbx") || ++ is_duplicate (type, mok, mok_size, &efi_guid_shim, "MokListXRT")) ++ return 0; + break; + case DELETE_MOK: + if (!is_duplicate (type, mok, mok_size, &efi_guid_shim, "MokListRT") || +@@ -1303,6 +1307,23 @@ is_ca_enrolled (void *mok, uint32_t mok_size, MokRequest req) + return 0; + } + ++/* Check whether the CA cert is blocked */ ++static int ++is_ca_blocked (void *mok, uint32_t mok_size, MokRequest req) ++{ ++ switch (req) { ++ case ENROLL_MOK: ++ if (is_ca_in_db (mok, mok_size, &efi_guid_security, "dbx") || ++ is_ca_in_db (mok, mok_size, &efi_guid_shim, "MokListXRT")) ++ return 1; ++ break; ++ default: ++ return 0; ++ } ++ ++ return 0; ++} ++ + static void + print_skip_message (const char *filename, void *mok, uint32_t mok_size, + MokRequest req) +@@ -1324,6 +1345,12 @@ print_skip_message (const char *filename, void *mok, uint32_t mok_size, + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokNew")) + printf ("SKIP: %s is already in the enrollment request\n", filename); ++ else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, ++ &efi_guid_security, "dbx")) ++ printf ("SKIP: %s is blocked in dbx\n", filename); ++ else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, ++ &efi_guid_shim, "MokListXRT")) ++ printf ("SKIP: %s is blocked in MokListXRT\n", filename); + break; + case DELETE_MOK: + if (!is_duplicate (&efi_guid_x509_cert, mok, mok_size, +@@ -1469,6 +1496,13 @@ issue_mok_request (char **files, uint32_t total, MokRequest req, + continue; + } + ++ /* Check whether CA is blocked */ ++ if (force_ca_check && is_ca_blocked (ptr, sizes[i], req)) { ++ printf ("CA blocked. Skip %s\n", files[i]); ++ close (fd); ++ continue; ++ } ++ + if (is_valid_request (&efi_guid_x509_cert, ptr, sizes[i], req)) { + ptr += sizes[i]; + real_size += sizes[i] + sizeof(EFI_SIGNATURE_LIST) + sizeof(efi_guid_t); +@@ -2127,6 +2161,12 @@ test_key (MokRequest req, const char *key_file) + goto error; + } + ++ if (force_ca_check && is_ca_blocked (key, read_size, req)) { ++ fprintf (stderr, "CA of %s is blocked\n", ++ key_file); ++ goto error; ++ } ++ + if (is_valid_request (&efi_guid_x509_cert, key, read_size, req)) { + printf ("%s is not enrolled\n", key_file); + ret = 0; +-- +2.28.0 + + +From 057f96e6842af030b1f68a609019043f0f853708 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Fri, 28 Aug 2020 11:58:12 +0800 +Subject: [PATCH 07/13] mokutil: improve the message from "--test-key" + +Print the details of the test result. + +Signed-off-by: Gary Lin +(cherry picked from commit 5ede0bd0d68d27afc6d3d06556d0077e2840502b) +--- + src/mokutil.c | 29 +++++++++++++++-------------- + 1 file changed, 15 insertions(+), 14 deletions(-) + +diff --git a/src/mokutil.c b/src/mokutil.c +index 834228a..e8b48fe 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -1332,49 +1332,49 @@ print_skip_message (const char *filename, void *mok, uint32_t mok_size, + case ENROLL_MOK: + if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_global, "PK")) +- printf ("SKIP: %s is already in PK\n", filename); ++ printf ("%s is already in PK\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_global, "KEK")) +- printf ("SKIP: %s is already in KEK\n", filename); ++ printf ("%s is already in KEK\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_security, "db")) +- printf ("SKIP: %s is already in db\n", filename); ++ printf ("%s is already in db\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokListRT")) +- printf ("SKIP: %s is already enrolled\n", filename); ++ printf ("%s is already enrolled\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokNew")) +- printf ("SKIP: %s is already in the enrollment request\n", filename); ++ printf ("%s is already in the enrollment request\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_security, "dbx")) +- printf ("SKIP: %s is blocked in dbx\n", filename); ++ printf ("%s is blocked in dbx\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokListXRT")) +- printf ("SKIP: %s is blocked in MokListXRT\n", filename); ++ printf ("%s is blocked in MokListXRT\n", filename); + break; + case DELETE_MOK: + if (!is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokListRT")) +- printf ("SKIP: %s is not in MokList\n", filename); ++ printf ("%s is not in MokList\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokDel")) +- printf ("SKIP: %s is already in the deletion request\n", filename); ++ printf ("%s is already in the deletion request\n", filename); + break; + case ENROLL_BLACKLIST: + if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokListXRT")) +- printf ("SKIP: %s is already in MokListX\n", filename); ++ printf ("%s is already in MokListX\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokXNew")) +- printf ("SKIP: %s is already in the MokX enrollment request\n", filename); ++ printf ("%s is already in the MokX enrollment request\n", filename); + break; + case DELETE_BLACKLIST: + if (!is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokListXRT")) +- printf ("SKIP: %s is not in MokListX\n", filename); ++ printf ("%s is not in MokListX\n", filename); + else if (is_duplicate (&efi_guid_x509_cert, mok, mok_size, + &efi_guid_shim, "MokXDel")) +- printf ("SKIP: %s is already in the MokX deletion request\n", filename); ++ printf ("%s is already in the MokX deletion request\n", filename); + break; + } + } +@@ -1511,6 +1511,7 @@ issue_mok_request (char **files, uint32_t total, MokRequest req, + reverse_req_names[req]); + ptr -= sizeof(EFI_SIGNATURE_LIST) + sizeof(efi_guid_t); + } else { ++ printf ("SKIP: "); + print_skip_message (files[i], ptr, sizes[i], req); + ptr -= sizeof(EFI_SIGNATURE_LIST) + sizeof(efi_guid_t); + } +@@ -2171,7 +2172,7 @@ test_key (MokRequest req, const char *key_file) + printf ("%s is not enrolled\n", key_file); + ret = 0; + } else { +- printf ("%s is already enrolled\n", key_file); ++ print_skip_message (key_file, key, read_size, req); + ret = 1; + } + +-- +2.28.0 + + +From 7e5d2cb51a8360ad461e1031b9b3280e72d6338c Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Wed, 2 Sep 2020 16:09:04 +0800 +Subject: [PATCH 08/13] mokutil: disable CA check by default + +The SUSE PTF certificate is also issued by SUSE CA, so enabling CA check +by default would ignore the enrollment of the PTF certificates and the +PTF would be unloadable. + +Flip "--ignore-ca-check" to "--ca-check" and set force_ca_check to 0 by +default. + +Signed-off-by: Gary Lin +(cherry picked from commit 235e92a1d3e0f32f7be44aa0f37d7f3041306ccc) +--- + src/mokutil.c | 10 +++++----- + 1 file changed, 5 insertions(+), 5 deletions(-) + +diff --git a/src/mokutil.c b/src/mokutil.c +index e8b48fe..b04deb3 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -183,7 +183,7 @@ print_help () + printf (" --root-pw\t\t\t\tUse the root password\n"); + printf (" --simple-hash\t\t\t\tUse the old password hash method\n"); + printf (" --mokx\t\t\t\tManipulate the MOK blacklist\n"); +- printf (" --ignore-ca-check\t\t\tDon't check CA of the given certificate\n"); ++ printf (" --ca-check\t\t\t\tCheck if CA of the key is enrolled/blocked\n"); + } + + static int +@@ -2342,7 +2342,7 @@ main (int argc, char *argv[]) + int ret = -1; + + use_simple_hash = 0; +- force_ca_check = 1; ++ force_ca_check = 0; + + if (!efi_variables_supported ()) { + fprintf (stderr, "EFI variables are not supported on this system\n"); +@@ -2383,7 +2383,7 @@ main (int argc, char *argv[]) + {"db", no_argument, 0, 0 }, + {"dbx", no_argument, 0, 0 }, + {"timeout", required_argument, 0, 0 }, +- {"ignore-ca-check", no_argument, 0, 0 }, ++ {"ca-check", no_argument, 0, 0 }, + {0, 0, 0, 0} + }; + +@@ -2470,8 +2470,8 @@ main (int argc, char *argv[]) + } else if (strcmp (option, "timeout") == 0) { + command |= TIMEOUT; + timeout = strdup (optarg); +- } else if (strcmp (option, "ignore-ca-check") == 0) { +- force_ca_check = 0; ++ } else if (strcmp (option, "ca-check") == 0) { ++ force_ca_check = 1; + } + + break; +-- +2.28.0 + + +From 8fee022cb2df7357bbc92c2c337af7b0057f1f23 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Wed, 2 Sep 2020 16:19:44 +0800 +Subject: [PATCH 09/13] man: add "--ca-check" to the man page + +Signed-off-by: Gary Lin +(cherry picked from commit ae0aaf1a62faaba16183ed01a7ac9406535d96a1) +--- + man/mokutil.1 | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +diff --git a/man/mokutil.1 b/man/mokutil.1 +index 25fe8b4..cb37484 100644 +--- a/man/mokutil.1 ++++ b/man/mokutil.1 +@@ -15,7 +15,7 @@ mokutil \- utility to manipulate machine owner keys + .br + \fBmokutil\fR [--import \fIkeylist\fR| -i \fIkeylist\fR] + ([--hash-file \fIhashfile\fR | -f \fIhashfile\fR] | [--root-pw | -P] | +- [--simple-hash | -s] | [--mokx | -X]) ++ [--simple-hash | -s] | [--mokx | -X] | [--ca-check]) + .br + \fBmokutil\fR [--delete \fIkeylist\fR | -d \fIkeylist\fR] + ([--hash-file \fIhashfile\fR | -f \fIhashfile\fR] | [--root-pw | -P] | +@@ -43,7 +43,7 @@ mokutil \- utility to manipulate machine owner keys + \fBmokutil\fR [--sb-state] + .br + \fBmokutil\fR [--test-key \fIkeyfile\fR | -t \fIkeyfile\fR] +- ([--mokx | -X]) ++ ([--mokx | -X] | [--ca-check]) + .br + \fBmokutil\fR [--reset] + ([--hash-file \fIhashfile\fR | -f \fIhashfile\fR] | [--root-pw | -P] | +@@ -173,3 +173,7 @@ List the keys in the secure boot signature store (db) + \fB--dbx\fR + List the keys in the secure boot blacklist signature store (dbx) + .TP ++\fB--ca-check\fR ++Check if the CA of the given key is already enrolled or blocked in the key ++databases. ++.TP +-- +2.28.0 + + +From cbada2d9ac9bfc36528a51dc9fcf136eb8290473 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Wed, 16 Sep 2020 11:59:02 +0800 +Subject: [PATCH 10/13] keyring: add the function to check kernel keyring + +Add match_skid_in_trusted_keyring() to check if the given SKID is in the +kernel trusted keys keyring. + +Signed-off-by: Gary Lin +(cherry picked from commit 9e5c6fd4fbdce386ecd2482a27f8a29e5d0c7eff) +--- + configure.ac | 1 + + src/Makefile.am | 4 ++ + src/keyring.c | 111 ++++++++++++++++++++++++++++++++++++++++++++++++ + src/keyring.h | 37 ++++++++++++++++ + 4 files changed, 153 insertions(+) + create mode 100644 src/keyring.c + create mode 100644 src/keyring.h + +diff --git a/configure.ac b/configure.ac +index d74fd21..b0b0376 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -85,6 +85,7 @@ AC_CHECK_FUNCS([memset]) + + PKG_CHECK_MODULES(OPENSSL, [openssl >= 0.9.8]) + PKG_CHECK_MODULES(EFIVAR, [efivar >= 0.12]) ++PKG_CHECK_MODULES(LIBKEYUTILS, [libkeyutils >= 1.5]) + + AC_ARG_WITH([bash-completion-dir], + AS_HELP_STRING([--with-bash-completion-dir[=PATH]], +diff --git a/src/Makefile.am b/src/Makefile.am +index 87b1515..f616b90 100644 +--- a/src/Makefile.am ++++ b/src/Makefile.am +@@ -2,13 +2,17 @@ bin_PROGRAMS = mokutil + + mokutil_CFLAGS = $(OPENSSL_CFLAGS) \ + $(EFIVAR_CFLAGS) \ ++ $(LIBKEYUTILS_CFLAGS) \ + $(WARNINGFLAGS_C) + + mokutil_LDADD = $(OPENSSL_LIBS) \ + $(EFIVAR_LIBS) \ ++ $(LIBKEYUTILS_LIBS) \ + -lcrypt + + mokutil_SOURCES = signature.h \ ++ keyring.h \ ++ keyring.c \ + password-crypt.h \ + password-crypt.c \ + mokutil.c +diff --git a/src/keyring.c b/src/keyring.c +new file mode 100644 +index 0000000..9709efd +--- /dev/null ++++ b/src/keyring.c +@@ -0,0 +1,111 @@ ++/** ++ * Copyright (C) 2020 Gary Lin ++ * ++ * This program is free software: you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License as published by ++ * the Free Software Foundation, either version 3 of the License, or ++ * (at your option) any later version. ++ * ++ * This program is distributed in the hope that it will be useful, ++ * but WITHOUT ANY WARRANTY; without even the implied warranty of ++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++ * GNU General Public License for more details. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program. If not, see . ++ * ++ * In addition, as a special exception, the copyright holders give ++ * permission to link the code of portions of this program with the ++ * OpenSSL library under certain conditions as described in each ++ * individual source file, and distribute linked combinations ++ * including the two. ++ * ++ * You must obey the GNU General Public License in all respects ++ * for all of the code used other than OpenSSL. If you modify ++ * file(s) with this exception, you may extend this exception to your ++ * version of the file(s), but you are not obligated to do so. If you ++ * do not wish to do so, delete this exception statement from your ++ * version. If you delete this exception statement from all source ++ * files in the program, then also delete it here. ++ */ ++ ++#include ++#include ++#include ++#include ++ ++#include ++ ++#include "keyring.h" ++ ++/** ++ * Match the x509v3 Subject Key ID in the descriptions of the kernel built-in ++ * trusted keys keyring ++ * ++ * return value ++ * - 0 : not matched ++ * - 1 : matched ++ * - -1 : error ++ */ ++int ++match_skid_in_trusted_keyring (const char *skid) ++{ ++ key_serial_t ring_id, key_id, *key_ptr; ++ void *keylist = NULL; ++ int count; ++ char buffer[1024]; ++ char *ptr; ++ long buf_size; ++ int ret = -1; ++ ++ if (skid == NULL) ++ return -1; ++ ++ /* Find the keyring ID of the kernel trusted keys */ ++ ring_id = find_key_by_type_and_desc("keyring", ".builtin_trusted_keys", 0); ++ if (ring_id < 0) { ++ fprintf(stderr, "Failed to accesss kernel trusted keyring: %m\n"); ++ goto out; ++ } ++ ++ count = keyctl_read_alloc(ring_id, &keylist); ++ if (count < 0) { ++ fprintf(stderr, "Failed to read kernel trusted keyring\n"); ++ goto out; ++ } ++ ++ count /= sizeof(key_serial_t); ++ if (count == 0) { ++ /* The keyring is empty */ ++ ret = 0; ++ goto out; ++ } ++ ++ /* Iterate the keylist and match SKID */ ++ key_ptr = keylist; ++ do { ++ key_id = *key_ptr++; ++ ++ buf_size = keyctl_describe(key_id, buffer, sizeof(buffer)); ++ if (buf_size < 0) { ++ fprintf(stderr, "key %X inaccessible %m\n", key_id); ++ goto out; ++ } ++ ++ /* Check if SKID is in the description */ ++ ptr = strstr(buffer, skid); ++ if (ptr && *(ptr + strlen(skid)) == '\0') { ++ /* Matched */ ++ ret = 1; ++ goto out; ++ } ++ } while (--count); ++ ++ ret = 0; ++out: ++ if (keylist) ++ free(keylist); ++ ++ return ret; ++ ++} +diff --git a/src/keyring.h b/src/keyring.h +new file mode 100644 +index 0000000..44127cf +--- /dev/null ++++ b/src/keyring.h +@@ -0,0 +1,37 @@ ++/** ++ * Copyright (C) 2020 Gary Lin ++ * ++ * This program is free software: you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License as published by ++ * the Free Software Foundation, either version 3 of the License, or ++ * (at your option) any later version. ++ * ++ * This program is distributed in the hope that it will be useful, ++ * but WITHOUT ANY WARRANTY; without even the implied warranty of ++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++ * GNU General Public License for more details. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program. If not, see . ++ * ++ * In addition, as a special exception, the copyright holders give ++ * permission to link the code of portions of this program with the ++ * OpenSSL library under certain conditions as described in each ++ * individual source file, and distribute linked combinations ++ * including the two. ++ * ++ * You must obey the GNU General Public License in all respects ++ * for all of the code used other than OpenSSL. If you modify ++ * file(s) with this exception, you may extend this exception to your ++ * version of the file(s), but you are not obligated to do so. If you ++ * do not wish to do so, delete this exception statement from your ++ * version. If you delete this exception statement from all source ++ * files in the program, then also delete it here. ++ */ ++ ++#ifndef __KEYRING_H__ ++#define __KEYRING_H__ ++ ++int match_skid_in_trusted_keyring (const char *skid); ++ ++#endif /* __KEYRING_H__ */ +-- +2.28.0 + + +From 8fc0f7bb5b9826fd3af99836a7e39fed607d3646 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Wed, 16 Sep 2020 12:00:18 +0800 +Subject: [PATCH 11/13] efi_x509: add the function to fetch SKID + +Add get_cert_skid() to fetch SKID of a given certiticate. + +Signed-off-by: Gary Lin +(cherry picked from commit 7a7a85ba5f057c0c155787d695561a051b6b5eb4) +--- + src/mokutil.c | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 57 insertions(+) + +diff --git a/src/mokutil.c b/src/mokutil.c +index b04deb3..e4e405e 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -47,6 +47,7 @@ + + #include + #include ++#include + + #include + #include +@@ -1034,6 +1035,62 @@ is_valid_cert (void *cert, uint32_t cert_size) + return 1; + } + ++/** ++ * Get the Subject Key Identifier of the given certificate ++ * ++ * This function allocates the SKID string and the caller is responsible to ++ * free the string. ++ * ++ * Return value: ++ * - 0 : Success ++ * - -1 : Error ++ */ ++static int ++get_cert_skid(const uint8_t *cert, const uint32_t cert_size, char **skid) ++{ ++ X509 *X509cert; ++ const ASN1_OCTET_STRING *asn1_id; ++ const uint8_t *data; ++ int data_len, i; ++ char *id_str, *ptr; ++ int ret = -1; ++ ++ X509cert = d2i_X509 (NULL, &cert, cert_size); ++ if (X509cert == NULL) { ++ fprintf (stderr, "invalid x509 certificate\n"); ++ goto out; ++ } ++ ++ asn1_id = X509_get0_subject_key_id (X509cert); ++ if (asn1_id == NULL) { ++ fprintf (stderr, "Failed to get Subject Key ID\n"); ++ goto out; ++ } ++ ++ data = ASN1_STRING_get0_data (asn1_id); ++ data_len = ASN1_STRING_length (asn1_id); ++ ++ id_str = malloc (data_len*2 + 1); ++ if (id_str == NULL) { ++ fprintf (stderr, "Failed to allocated id string\n"); ++ goto out; ++ } ++ ++ ptr = id_str; ++ for (i = 0; i < data_len; i++) { ++ snprintf (ptr, 3, "%02x", data[i]); ++ ptr += 2; ++ } ++ ++ *skid = id_str; ++ ret = 0; ++out: ++ if (X509cert) ++ X509_free (X509cert); ++ ++ return ret; ++} ++ + /** + * Check whether the given CA cert is the immediate CA of the given cert + **/ +-- +2.28.0 + + +From 8f8ee97cd068eaeabe6897314f63bc4a5606b97c Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Wed, 16 Sep 2020 12:03:33 +0800 +Subject: [PATCH 12/13] mokutil: check the kernel trusted keyring by default + +When enrolling a new key, mokutil now checks whether the key is one of +the kernel built-in trusted keys. + +The kernel keyring check can be disabled by "--ignore-keyring". + +Signed-off-by: Gary Lin +(cherry picked from commit 8bac3f53e2c4600f0843234e1b525a816f255955) +--- + src/mokutil.c | 41 +++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 41 insertions(+) + +diff --git a/src/mokutil.c b/src/mokutil.c +index e4e405e..02ed21f 100644 +--- a/src/mokutil.c ++++ b/src/mokutil.c +@@ -53,6 +53,7 @@ + #include + + #include "signature.h" ++#include "keyring.h" + #include "password-crypt.h" + + #define PASSWORD_MAX 256 +@@ -97,6 +98,7 @@ typedef wchar_t efi_char16_t; /* UNICODE character */ + + static int use_simple_hash; + static int force_ca_check; ++static int check_keyring; + + typedef enum { + DELETE_MOK = 0, +@@ -185,6 +187,7 @@ print_help () + printf (" --simple-hash\t\t\t\tUse the old password hash method\n"); + printf (" --mokx\t\t\t\tManipulate the MOK blacklist\n"); + printf (" --ca-check\t\t\t\tCheck if CA of the key is enrolled/blocked\n"); ++ printf (" --ignore-keyring\t\t\tDon't check if the key is the kernel keyring\n"); + } + + static int +@@ -1381,6 +1384,25 @@ is_ca_blocked (void *mok, uint32_t mok_size, MokRequest req) + return 0; + } + ++/* Check whether the key is already in the kernel trusted keyring */ ++static int ++is_in_trusted_keyring (const void *cert, const uint32_t cert_size) ++{ ++ char *skid = NULL; ++ int ret; ++ ++ if (get_cert_skid (cert, cert_size, &skid) < 0) ++ return 0; ++ ++ ret = match_skid_in_trusted_keyring (skid); ++ if (ret < 0) ++ ret = 0; ++ ++ free (skid); ++ ++ return ret; ++} ++ + static void + print_skip_message (const char *filename, void *mok, uint32_t mok_size, + MokRequest req) +@@ -1546,6 +1568,15 @@ issue_mok_request (char **files, uint32_t total, MokRequest req, + goto error; + } + ++ /* Check whether the key is already in the trusted keyring */ ++ if (req == ENROLL_MOK && check_keyring && ++ is_in_trusted_keyring (ptr, sizes[i])) { ++ printf ("Already in kernel trusted keyring. Skip %s\n", ++ files[i]); ++ close (fd); ++ continue; ++ } ++ + /* Check whether CA is already enrolled */ + if (force_ca_check && is_ca_enrolled (ptr, sizes[i], req)) { + printf ("CA enrolled. Skip %s\n", files[i]); +@@ -2213,6 +2244,12 @@ test_key (MokRequest req, const char *key_file) + goto error; + } + ++ if (check_keyring && is_in_trusted_keyring (key, read_size)) { ++ fprintf (stderr, "%s is already in the built-in trusted keyring\n", ++ key_file); ++ goto error; ++ } ++ + if (force_ca_check && is_ca_enrolled (key, read_size, req)) { + fprintf (stderr, "CA of %s is already enrolled\n", + key_file); +@@ -2400,6 +2437,7 @@ main (int argc, char *argv[]) + + use_simple_hash = 0; + force_ca_check = 0; ++ check_keyring = 1; + + if (!efi_variables_supported ()) { + fprintf (stderr, "EFI variables are not supported on this system\n"); +@@ -2441,6 +2479,7 @@ main (int argc, char *argv[]) + {"dbx", no_argument, 0, 0 }, + {"timeout", required_argument, 0, 0 }, + {"ca-check", no_argument, 0, 0 }, ++ {"ignore-keyring", no_argument, 0, 0 }, + {0, 0, 0, 0} + }; + +@@ -2529,6 +2568,8 @@ main (int argc, char *argv[]) + timeout = strdup (optarg); + } else if (strcmp (option, "ca-check") == 0) { + force_ca_check = 1; ++ } else if (strcmp (option, "ignore-keyring") == 0) { ++ check_keyring = 0; + } + + break; +-- +2.28.0 + + +From 4a1e8c43ada0896ed169826ae9cfc7c83d4d7f27 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Wed, 16 Sep 2020 16:10:29 +0800 +Subject: [PATCH 13/13] man: add "--ignore-keyring" + +Signed-off-by: Gary Lin +(cherry picked from commit c24deaa37d72f8aa06cf22d35c91b218d1a3d99e) +--- + man/mokutil.1 | 7 +++++-- + 1 file changed, 5 insertions(+), 2 deletions(-) + +diff --git a/man/mokutil.1 b/man/mokutil.1 +index cb37484..cbea367 100644 +--- a/man/mokutil.1 ++++ b/man/mokutil.1 +@@ -15,7 +15,7 @@ mokutil \- utility to manipulate machine owner keys + .br + \fBmokutil\fR [--import \fIkeylist\fR| -i \fIkeylist\fR] + ([--hash-file \fIhashfile\fR | -f \fIhashfile\fR] | [--root-pw | -P] | +- [--simple-hash | -s] | [--mokx | -X] | [--ca-check]) ++ [--simple-hash | -s] | [--mokx | -X] | [--ca-check] | [--ignore-keyring]) + .br + \fBmokutil\fR [--delete \fIkeylist\fR | -d \fIkeylist\fR] + ([--hash-file \fIhashfile\fR | -f \fIhashfile\fR] | [--root-pw | -P] | +@@ -43,7 +43,7 @@ mokutil \- utility to manipulate machine owner keys + \fBmokutil\fR [--sb-state] + .br + \fBmokutil\fR [--test-key \fIkeyfile\fR | -t \fIkeyfile\fR] +- ([--mokx | -X] | [--ca-check]) ++ ([--mokx | -X] | [--ca-check] | [--ignore-keyring]) + .br + \fBmokutil\fR [--reset] + ([--hash-file \fIhashfile\fR | -f \fIhashfile\fR] | [--root-pw | -P] | +@@ -177,3 +177,6 @@ List the keys in the secure boot blacklist signature store (dbx) + Check if the CA of the given key is already enrolled or blocked in the key + databases. + .TP ++\fB--ignore-keyring\fR ++Ignore the kernel builtin trusted keys keyring check when enrolling a key into MokList ++.TP +-- +2.28.0 + diff --git a/mokutil-remove-libkeyutils-check.patch b/mokutil-remove-libkeyutils-check.patch new file mode 100644 index 0000000..cb5c89e --- /dev/null +++ b/mokutil-remove-libkeyutils-check.patch @@ -0,0 +1,46 @@ +From 87eb098c85dcae328924e91bb84e8e68ea15fd15 Mon Sep 17 00:00:00 2001 +From: Gary Lin +Date: Wed, 16 Sep 2020 17:02:56 +0800 +Subject: [PATCH] Remove libkeyutils pkgconfig check + +keyutils didn't provide pkgconfig in 1.5.* + +Signed-off-by: Gary Lin +--- + configure.ac | 1 - + src/Makefile.am | 3 +-- + 2 files changed, 1 insertion(+), 3 deletions(-) + +diff --git a/configure.ac b/configure.ac +index b0b0376..d74fd21 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -85,7 +85,6 @@ AC_CHECK_FUNCS([memset]) + + PKG_CHECK_MODULES(OPENSSL, [openssl >= 0.9.8]) + PKG_CHECK_MODULES(EFIVAR, [efivar >= 0.12]) +-PKG_CHECK_MODULES(LIBKEYUTILS, [libkeyutils >= 1.5]) + + AC_ARG_WITH([bash-completion-dir], + AS_HELP_STRING([--with-bash-completion-dir[=PATH]], +diff --git a/src/Makefile.am b/src/Makefile.am +index f616b90..664b80a 100644 +--- a/src/Makefile.am ++++ b/src/Makefile.am +@@ -2,12 +2,11 @@ bin_PROGRAMS = mokutil + + mokutil_CFLAGS = $(OPENSSL_CFLAGS) \ + $(EFIVAR_CFLAGS) \ +- $(LIBKEYUTILS_CFLAGS) \ + $(WARNINGFLAGS_C) + + mokutil_LDADD = $(OPENSSL_LIBS) \ + $(EFIVAR_LIBS) \ +- $(LIBKEYUTILS_LIBS) \ ++ -lkeyutils \ + -lcrypt + + mokutil_SOURCES = signature.h \ +-- +2.28.0 + diff --git a/mokutil-support-revoke-builtin-cert.patch b/mokutil-support-revoke-builtin-cert.patch index acd0a10..c933057 100644 --- a/mokutil-support-revoke-builtin-cert.patch +++ b/mokutil-support-revoke-builtin-cert.patch @@ -1,4 +1,4 @@ -From 93ded288224a18f336f9e3654a33a48bcb748b11 Mon Sep 17 00:00:00 2001 +From df2a6b1cc6e1763e1ed1b8e59b012ae8dc048a81 Mon Sep 17 00:00:00 2001 From: Gary Ching-Pang Lin Date: Fri, 21 Feb 2014 17:56:55 +0800 Subject: [PATCH 1/4] Add the option to revoke the built-in certificate @@ -13,10 +13,10 @@ revoke the built-in certificate. 1 file changed, 82 insertions(+) diff --git a/src/mokutil.c b/src/mokutil.c -index e2d567d..1ada2a0 100644 +index 02ed21f..d95a2eb 100644 --- a/src/mokutil.c +++ b/src/mokutil.c -@@ -84,6 +84,7 @@ +@@ -86,6 +86,7 @@ #define DELETE_HASH (1 << 22) #define VERBOSITY (1 << 23) #define TIMEOUT (1 << 24) @@ -24,7 +24,7 @@ index e2d567d..1ada2a0 100644 #define DEFAULT_CRYPT_METHOD SHA512_BASED #define DEFAULT_SALT_SIZE SHA512_SALT_MAX -@@ -176,6 +177,7 @@ print_help () +@@ -180,6 +181,7 @@ print_help () printf (" --db\t\t\t\t\tList the keys in db\n"); printf (" --dbx\t\t\t\t\tList the keys in dbx\n"); printf (" --timeout <-1,0..0x7fff>\t\tSet the timeout for MOK prompt\n"); @@ -32,7 +32,7 @@ index e2d567d..1ada2a0 100644 printf ("\n"); printf ("Supplimentary Options:\n"); printf (" --hash-file \t\tUse the specific password hash\n"); -@@ -2103,6 +2105,79 @@ set_verbosity (uint8_t verbosity) +@@ -2397,6 +2399,79 @@ set_verbosity (uint8_t verbosity) return 0; } @@ -112,24 +112,24 @@ index e2d567d..1ada2a0 100644 static inline int list_db (DBName db_name) { -@@ -2182,6 +2257,7 @@ main (int argc, char *argv[]) - {"db", no_argument, 0, 0 }, - {"dbx", no_argument, 0, 0 }, +@@ -2480,6 +2555,7 @@ main (int argc, char *argv[]) {"timeout", required_argument, 0, 0 }, + {"ca-check", no_argument, 0, 0 }, + {"ignore-keyring", no_argument, 0, 0 }, + {"revoke-cert", no_argument, 0, 0 }, {0, 0, 0, 0} }; -@@ -2268,6 +2344,8 @@ main (int argc, char *argv[]) - } else if (strcmp (option, "timeout") == 0) { - command |= TIMEOUT; - timeout = strdup (optarg); +@@ -2570,6 +2646,8 @@ main (int argc, char *argv[]) + force_ca_check = 1; + } else if (strcmp (option, "ignore-keyring") == 0) { + check_keyring = 0; + } else if (strcmp (option, "revoke-cert") == 0) { + command |= REVOKE_CERT; } break; -@@ -2537,6 +2615,10 @@ main (int argc, char *argv[]) +@@ -2839,6 +2917,10 @@ main (int argc, char *argv[]) case TIMEOUT: ret = set_timeout (timeout); break; @@ -141,10 +141,10 @@ index e2d567d..1ada2a0 100644 print_help (); break; -- -2.27.0 +2.28.0 -From 17f9850edce4dd40f96107c97d3d720406bf9f09 Mon Sep 17 00:00:00 2001 +From 819accd580465aa21da7bed081790c6c9e889702 Mon Sep 17 00:00:00 2001 From: Gary Ching-Pang Lin Date: Tue, 4 Nov 2014 14:50:36 +0800 Subject: [PATCH 2/4] Use the efivar functions to access UEFI variables @@ -157,10 +157,10 @@ Adapt the changes in the mainline. 1 file changed, 25 insertions(+), 20 deletions(-) diff --git a/src/mokutil.c b/src/mokutil.c -index 1ada2a0..dcf55dc 100644 +index d95a2eb..8be0b77 100644 --- a/src/mokutil.c +++ b/src/mokutil.c -@@ -2108,28 +2108,35 @@ set_verbosity (uint8_t verbosity) +@@ -2402,28 +2402,35 @@ set_verbosity (uint8_t verbosity) static int revoke_builtin_cert (void) { @@ -205,7 +205,7 @@ index 1ada2a0..dcf55dc 100644 memset (&pw_crypt, 0, sizeof(pw_crypt_t)); memset (auth, 0, SHA256_DIGEST_LENGTH); -@@ -2152,20 +2159,18 @@ revoke_builtin_cert (void) +@@ -2446,20 +2453,18 @@ revoke_builtin_cert (void) } if (!use_simple_hash) { @@ -236,10 +236,10 @@ index 1ada2a0..dcf55dc 100644 goto error; } -- -2.27.0 +2.28.0 -From 1ab85ee4d98a5436c4612b8f893c3c73f113a6e0 Mon Sep 17 00:00:00 2001 +From 2627cdff19e6e998180690151c9cc6533fff6cc1 Mon Sep 17 00:00:00 2001 From: Gary Lin Date: Wed, 13 Jul 2016 14:58:15 +0800 Subject: [PATCH 3/4] Use efi_set_variable from efivar 0.24 @@ -250,10 +250,10 @@ This is an openSUSE-only patch. 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/mokutil.c b/src/mokutil.c -index dcf55dc..0160c06 100644 +index 8be0b77..f27bba0 100644 --- a/src/mokutil.c +++ b/src/mokutil.c -@@ -2170,7 +2170,8 @@ revoke_builtin_cert (void) +@@ -2464,7 +2464,8 @@ revoke_builtin_cert (void) | EFI_VARIABLE_RUNTIME_ACCESS; if (efi_set_variable (efi_guid_shim, "ClearVerify", @@ -264,10 +264,10 @@ index dcf55dc..0160c06 100644 goto error; } -- -2.27.0 +2.28.0 -From ca9db2e9aa89a945651787b23046a6213af4144d Mon Sep 17 00:00:00 2001 +From acbf5198afdec419f4ae17dc140cd093906e0a00 Mon Sep 17 00:00:00 2001 From: Gary Lin Date: Fri, 14 Aug 2020 14:57:23 +0800 Subject: [PATCH 4/4] man: add "--revoke-cert" @@ -282,7 +282,7 @@ Signed-off-by: Gary Lin 1 file changed, 5 insertions(+) diff --git a/man/mokutil.1 b/man/mokutil.1 -index 25fe8b4..bf27a52 100644 +index cbea367..1c18d7a 100644 --- a/man/mokutil.1 +++ b/man/mokutil.1 @@ -73,6 +73,8 @@ mokutil \- utility to manipulate machine owner keys @@ -294,13 +294,13 @@ index 25fe8b4..bf27a52 100644 .SH DESCRIPTION \fBmokutil\fR is a tool to import or delete the machines owner keys -@@ -173,3 +175,6 @@ List the keys in the secure boot signature store (db) - \fB--dbx\fR - List the keys in the secure boot blacklist signature store (dbx) +@@ -180,3 +182,6 @@ databases. + \fB--ignore-keyring\fR + Ignore the kernel builtin trusted keys keyring check when enrolling a key into MokList .TP +\fB--revoke-cert\fR +Revoke the agreement of using the built-in certificate in shim (openSUSE Specfic) +.TP -- -2.27.0 +2.28.0 diff --git a/mokutil.changes b/mokutil.changes index 556ab4d..12d1747 100644 --- a/mokutil.changes +++ b/mokutil.changes @@ -1,3 +1,13 @@ +------------------------------------------------------------------- +Wed Sep 16 09:06:02 UTC 2020 - Gary Ching-Pang Lin + +- Add mokutil-bsc1173115-add-ca-and-keyring-checks.patch to add + options for CA and kernel keyring checks (bsc#1173115) + + Add new BuildRequires: keyutils-devel + + Add mokutil-remove-libkeyutils-check.patch to disable the + version check of libkeyutils +- Refresh mokutil-support-revoke-builtin-cert.patch + ------------------------------------------------------------------- Fri Aug 14 06:59:46 UTC 2020 - Gary Ching-Pang Lin diff --git a/mokutil.spec b/mokutil.spec index 7c50a10..70dcdbe 100644 --- a/mokutil.spec +++ b/mokutil.spec @@ -27,10 +27,15 @@ Source: https://github.com/lcp/%{name}/archive/%{version}.tar.gz Source1: modhash # PATCH-FIX-UPSTREAM mokutil-remove-shebang-from-bash-completion-file.patch glin@suse.com -- Remove shebang from bash-completion/mokutil Patch1: mokutil-remove-shebang-from-bash-completion-file.patch +# PATCH-FIX-UPSTREAM mokutil-bsc1173115-add-ca-and-keyring-checks.patch bsc#1173115 glin@suse.com -- Add options for CA and kernel keyring checks +Patch2: mokutil-bsc1173115-add-ca-and-keyring-checks.patch +# PATCH-FIX-SUSE mokutil-remove-libkeyutils-check.patch glin@suse.com -- Disable the check of libkeyutils version +Patch3: mokutil-remove-libkeyutils-check.patch Patch100: mokutil-support-revoke-builtin-cert.patch BuildRequires: autoconf BuildRequires: automake BuildRequires: efivar-devel >= 0.12 +BuildRequires: keyutils-devel >= 1.5.0 BuildRequires: libopenssl-devel >= 0.9.8 BuildRequires: pkg-config Requires: openssl @@ -50,6 +55,8 @@ Authors: %prep %setup -q %patch1 -p1 +%patch2 -p1 +%patch3 -p1 %patch100 -p1 %build