• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

randombit / botan / 19012754211

02 Nov 2025 01:10PM UTC coverage: 90.677% (+0.006%) from 90.671%
19012754211

push

github

web-flow
Merge pull request #5137 from randombit/jack/clang-tidy-includes

Remove various unused includes flagged by clang-tidy misc-include-cleaner

100457 of 110786 relevant lines covered (90.68%)

12189873.8 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

89.06
/src/lib/x509/x509self.cpp
1
/*
2
* PKCS #10/Self Signed Cert Creation
3
* (C) 1999-2008,2018 Jack Lloyd
4
*
5
* Botan is released under the Simplified BSD License (see license.txt)
6
*/
7

8
#include <botan/x509self.h>
9

10
#include <botan/assert.h>
11
#include <botan/pubkey.h>
12
#include <botan/x509_ca.h>
13
#include <botan/x509_ext.h>
14
#include <botan/x509_key.h>
15
#include <botan/internal/fmt.h>
16
#include <botan/internal/parsing.h>
17

18
namespace Botan {
19

20
namespace {
21

22
/*
23
* Load information from the X509_Cert_Options
24
*/
25
X509_DN load_dn_info(const X509_Cert_Options& opts) {
1,775✔
26
   X509_DN subject_dn;
1,775✔
27

28
   subject_dn.add_attribute("X520.CommonName", opts.common_name);
1,775✔
29
   subject_dn.add_attribute("X520.Country", opts.country);
1,775✔
30
   subject_dn.add_attribute("X520.State", opts.state);
1,775✔
31
   subject_dn.add_attribute("X520.Locality", opts.locality);
1,775✔
32
   subject_dn.add_attribute("X520.Organization", opts.organization);
1,775✔
33
   subject_dn.add_attribute("X520.OrganizationalUnit", opts.org_unit);
1,775✔
34
   subject_dn.add_attribute("X520.SerialNumber", opts.serial_number);
1,775✔
35

36
   for(const auto& extra_ou : opts.more_org_units) {
1,797✔
37
      subject_dn.add_attribute("X520.OrganizationalUnit", extra_ou);
22✔
38
   }
39

40
   return subject_dn;
1,775✔
41
}
×
42

43
auto create_alt_name_ext(const X509_Cert_Options& opts, const Extensions& extensions) {
1,775✔
44
   AlternativeName subject_alt;
1,775✔
45

46
   /*
47
   If the extension was already created in opts.extension we need to
48
   merge the values provided in opts with the values set in the extension.
49
   */
50
   if(const auto* ext = extensions.get_extension_object_as<Cert_Extension::Subject_Alternative_Name>()) {
1,775✔
51
      subject_alt = ext->get_alt_name();
11✔
52
   }
53

54
   subject_alt.add_dns(opts.dns);
1,775✔
55
   for(const auto& nm : opts.more_dns) {
1,812✔
56
      subject_alt.add_dns(nm);
37✔
57
   }
58
   subject_alt.add_uri(opts.uri);
1,775✔
59
   subject_alt.add_email(opts.email);
1,775✔
60
   if(!opts.ip.empty()) {
1,775✔
61
      if(auto ipv4 = string_to_ipv4(opts.ip)) {
×
62
         subject_alt.add_ipv4_address(*ipv4);
×
63
      } else {
64
         throw Invalid_Argument(fmt("Invalid IPv4 address '{}'", opts.ip));
×
65
      }
66
   }
67

68
   if(!opts.xmpp.empty()) {
1,775✔
69
      subject_alt.add_other_name(OID::from_string("PKIX.XMPPAddr"), ASN1_String(opts.xmpp, ASN1_Type::Utf8String));
×
70
   }
71

72
   return std::make_unique<Cert_Extension::Subject_Alternative_Name>(subject_alt);
3,550✔
73
}
1,775✔
74

75
}  // namespace
76

77
namespace X509 {
78

79
/*
80
* Create a new self-signed X.509 certificate
81
*/
82
X509_Certificate create_self_signed_cert(const X509_Cert_Options& opts,
228✔
83
                                         const Private_Key& key,
84
                                         std::string_view hash_fn,
85
                                         RandomNumberGenerator& rng) {
86
   const std::vector<uint8_t> pub_key = X509::BER_encode(key);
228✔
87
   auto signer = X509_Object::choose_sig_format(key, rng, hash_fn, opts.padding_scheme);
228✔
88
   const AlgorithmIdentifier sig_algo = signer->algorithm_identifier();
228✔
89
   BOTAN_ASSERT_NOMSG(sig_algo.oid().has_value());
227✔
90

91
   const auto subject_dn = load_dn_info(opts);
227✔
92

93
   Extensions extensions = opts.extensions;
227✔
94

95
   const auto constraints = opts.is_CA ? Key_Constraints::ca_constraints() : opts.constraints;
227✔
96

97
   if(!constraints.compatible_with(key)) {
227✔
98
      throw Invalid_Argument("The requested key constraints are incompatible with the algorithm");
×
99
   }
100

101
   extensions.add_new(std::make_unique<Cert_Extension::Basic_Constraints>(opts.is_CA, opts.path_limit), true);
454✔
102

103
   if(!constraints.empty()) {
227✔
104
      extensions.add_new(std::make_unique<Cert_Extension::Key_Usage>(constraints), true);
442✔
105
   }
106

107
   auto skid = std::make_unique<Cert_Extension::Subject_Key_ID>(pub_key, signer->hash_function());
227✔
108

109
   extensions.add_new(std::make_unique<Cert_Extension::Authority_Key_ID>(skid->get_key_id()));
454✔
110
   extensions.add_new(std::move(skid));
227✔
111

112
   extensions.replace(create_alt_name_ext(opts, extensions));
454✔
113

114
   extensions.add_new(std::make_unique<Cert_Extension::Extended_Key_Usage>(opts.ex_constraints));
454✔
115

116
   return X509_CA::make_cert(*signer, rng, sig_algo, pub_key, opts.start, opts.end, subject_dn, subject_dn, extensions);
454✔
117
}
910✔
118

119
/*
120
* Create a PKCS #10 certificate request
121
*/
122
PKCS10_Request create_cert_req(const X509_Cert_Options& opts,
1,548✔
123
                               const Private_Key& key,
124
                               std::string_view hash_fn,
125
                               RandomNumberGenerator& rng) {
126
   const auto subject_dn = load_dn_info(opts);
1,548✔
127

128
   const auto constraints = opts.is_CA ? Key_Constraints::ca_constraints() : opts.constraints;
1,548✔
129

130
   if(!constraints.compatible_with(key)) {
1,548✔
131
      throw Invalid_Argument("The requested key constraints are incompatible with the algorithm");
×
132
   }
133

134
   Extensions extensions = opts.extensions;
1,548✔
135

136
   extensions.add_new(std::make_unique<Cert_Extension::Basic_Constraints>(opts.is_CA, opts.path_limit));
3,096✔
137

138
   if(!constraints.empty()) {
1,548✔
139
      extensions.add_new(std::make_unique<Cert_Extension::Key_Usage>(constraints));
2,848✔
140
   }
141

142
   extensions.replace(create_alt_name_ext(opts, extensions));
3,096✔
143

144
   if(!opts.ex_constraints.empty()) {
1,548✔
145
      extensions.add_new(std::make_unique<Cert_Extension::Extended_Key_Usage>(opts.ex_constraints));
22✔
146
   }
147

148
   return PKCS10_Request::create(key, subject_dn, extensions, hash_fn, rng, opts.padding_scheme, opts.challenge);
1,548✔
149
}
3,096✔
150

151
}  // namespace X509
152

153
}  // namespace Botan
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc