blob: 87e8ff67ae1158e5bf7040a92579c8a4c40fa86c [file] [log] [blame]
Raymond Mao0d2d4b02024-10-03 14:50:26 -07001// SPDX-License-Identifier: GPL-2.0+
2/*
3 * X509 helper functions
4 *
5 * Copyright (C) 2012 Red Hat, Inc. All Rights Reserved.
6 * Written by David Howells (dhowells@redhat.com)
7 */
8#include <linux/err.h>
9#include <crypto/public_key.h>
10#include <crypto/x509_parser.h>
11
12/*
13 * Check for self-signedness in an X.509 cert and if found, check the signature
14 * immediately if we can.
15 */
16int x509_check_for_self_signed(struct x509_certificate *cert)
17{
18 int ret = 0;
19
20 if (cert->raw_subject_size != cert->raw_issuer_size ||
21 memcmp(cert->raw_subject, cert->raw_issuer,
22 cert->raw_issuer_size))
23 goto not_self_signed;
24
25 if (cert->sig->auth_ids[0] || cert->sig->auth_ids[1]) {
26 /*
27 * If the AKID is present it may have one or two parts. If
28 * both are supplied, both must match.
29 */
30 bool a = asymmetric_key_id_same(cert->skid,
31 cert->sig->auth_ids[1]);
32 bool b = asymmetric_key_id_same(cert->id,
33 cert->sig->auth_ids[0]);
34
35 if (!a && !b)
36 goto not_self_signed;
37
38 ret = -EKEYREJECTED;
39 if (((a && !b) || (b && !a)) &&
40 cert->sig->auth_ids[0] && cert->sig->auth_ids[1])
41 goto out;
42 }
43
44 ret = -EKEYREJECTED;
45 if (strcmp(cert->pub->pkey_algo, cert->sig->pkey_algo))
46 goto out;
47
48 ret = public_key_verify_signature(cert->pub, cert->sig);
49 if (ret == -ENOPKG) {
50 cert->unsupported_sig = true;
51 goto not_self_signed;
52 }
53 if (ret < 0)
54 goto out;
55
56 pr_devel("Cert Self-signature verified");
57 cert->self_signed = true;
58
59out:
60 return ret;
61
62not_self_signed:
63 return 0;
64}