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

randombit / botan / 5079590438

25 May 2023 12:28PM UTC coverage: 92.228% (+0.5%) from 91.723%
5079590438

Pull #3502

github

Pull Request #3502: Apply clang-format to the codebase

75589 of 81959 relevant lines covered (92.23%)

12139530.51 hits per line

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

98.48
/src/lib/modes/cipher_mode.cpp
1
/*
2
* Cipher Modes
3
* (C) 2015 Jack Lloyd
4
*
5
* Botan is released under the Simplified BSD License (see license.txt)
6
*/
7

8
#include <botan/cipher_mode.h>
9

10
#include <botan/internal/parsing.h>
11
#include <botan/internal/scan_name.h>
12
#include <botan/internal/stream_mode.h>
13
#include <sstream>
14

15
#if defined(BOTAN_HAS_BLOCK_CIPHER)
16
   #include <botan/block_cipher.h>
17
#endif
18

19
#if defined(BOTAN_HAS_AEAD_MODES)
20
   #include <botan/aead.h>
21
#endif
22

23
#if defined(BOTAN_HAS_MODE_CBC)
24
   #include <botan/internal/cbc.h>
25
#endif
26

27
#if defined(BOTAN_HAS_MODE_CFB)
28
   #include <botan/internal/cfb.h>
29
#endif
30

31
#if defined(BOTAN_HAS_MODE_XTS)
32
   #include <botan/internal/xts.h>
33
#endif
34

35
#if defined(BOTAN_HAS_COMMONCRYPTO)
36
   #include <botan/internal/commoncrypto.h>
37
#endif
38

39
namespace Botan {
40

41
std::unique_ptr<Cipher_Mode> Cipher_Mode::create_or_throw(std::string_view algo,
165✔
42
                                                          Cipher_Dir direction,
43
                                                          std::string_view provider) {
44
   if(auto mode = Cipher_Mode::create(algo, direction, provider))
165✔
45
      return mode;
164✔
46

47
   throw Lookup_Error("Cipher mode", algo, provider);
1✔
48
}
49

50
std::unique_ptr<Cipher_Mode> Cipher_Mode::create(std::string_view algo,
20,265✔
51
                                                 Cipher_Dir direction,
52
                                                 std::string_view provider) {
53
#if defined(BOTAN_HAS_COMMONCRYPTO)
54
   if(provider.empty() || provider == "commoncrypto") {
55
      auto commoncrypto_cipher = make_commoncrypto_cipher_mode(algo, direction);
56

57
      if(commoncrypto_cipher)
58
         return commoncrypto_cipher;
59

60
      if(!provider.empty())
61
         return std::unique_ptr<Cipher_Mode>();
62
   }
63
#endif
64

65
#if defined(BOTAN_HAS_STREAM_CIPHER)
66
   if(auto sc = StreamCipher::create(algo)) {
20,265✔
67
      return std::make_unique<Stream_Cipher_Mode>(std::move(sc));
57✔
68
   }
57✔
69
#endif
70

71
#if defined(BOTAN_HAS_AEAD_MODES)
72
   if(auto aead = AEAD_Mode::create(algo, direction)) {
20,208✔
73
      return aead;
3,842✔
74
   }
3,842✔
75
#endif
76

77
   if(algo.find('/') != std::string::npos) {
16,366✔
78
      const std::vector<std::string> algo_parts = split_on(algo, '/');
8,182✔
79
      std::string_view cipher_name = algo_parts[0];
8,182✔
80
      const std::vector<std::string> mode_info = parse_algorithm_name(algo_parts[1]);
8,182✔
81

82
      if(mode_info.empty())
8,182✔
83
         return std::unique_ptr<Cipher_Mode>();
×
84

85
      std::ostringstream mode_name;
8,182✔
86

87
      mode_name << mode_info[0] << '(' << cipher_name;
8,182✔
88
      for(size_t i = 1; i < mode_info.size(); ++i)
8,460✔
89
         mode_name << ',' << mode_info[i];
278✔
90
      for(size_t i = 2; i < algo_parts.size(); ++i)
10,175✔
91
         mode_name << ',' << algo_parts[i];
1,993✔
92
      mode_name << ')';
8,182✔
93

94
      return Cipher_Mode::create(mode_name.str(), direction, provider);
8,182✔
95
   }
8,182✔
96

97
#if defined(BOTAN_HAS_BLOCK_CIPHER)
98

99
   SCAN_Name spec(algo);
8,184✔
100

101
   if(spec.arg_count() == 0) {
8,184✔
102
      return std::unique_ptr<Cipher_Mode>();
42✔
103
   }
104

105
   auto bc = BlockCipher::create(spec.arg(0), provider);
8,142✔
106

107
   if(!bc) {
8,142✔
108
      return std::unique_ptr<Cipher_Mode>();
1,245✔
109
   }
110

111
   #if defined(BOTAN_HAS_MODE_CBC)
112
   if(spec.algo_name() == "CBC") {
13,794✔
113
      const std::string padding = spec.arg(1, "PKCS7");
2,323✔
114

115
      if(padding == "CTS") {
2,323✔
116
         if(direction == Cipher_Dir::Encryption)
240✔
117
            return std::make_unique<CTS_Encryption>(std::move(bc));
144✔
118
         else
119
            return std::make_unique<CTS_Decryption>(std::move(bc));
96✔
120
      } else {
121
         auto pad = BlockCipherModePaddingMethod::create(padding);
2,083✔
122

123
         if(pad) {
2,083✔
124
            if(direction == Cipher_Dir::Encryption)
2,083✔
125
               return std::make_unique<CBC_Encryption>(std::move(bc), std::move(pad));
1,205✔
126
            else
127
               return std::make_unique<CBC_Decryption>(std::move(bc), std::move(pad));
878✔
128
         }
129
      }
2,083✔
130
   }
2,323✔
131
   #endif
132

133
   #if defined(BOTAN_HAS_MODE_XTS)
134
   if(spec.algo_name() == "XTS") {
9,148✔
135
      if(direction == Cipher_Dir::Encryption)
4,175✔
136
         return std::make_unique<XTS_Encryption>(std::move(bc));
2,505✔
137
      else
138
         return std::make_unique<XTS_Decryption>(std::move(bc));
1,670✔
139
   }
140
   #endif
141

142
   #if defined(BOTAN_HAS_MODE_CFB)
143
   if(spec.algo_name() == "CFB") {
798✔
144
      const size_t feedback_bits = spec.arg_as_integer(1, 8 * bc->block_size());
399✔
145
      if(direction == Cipher_Dir::Encryption)
399✔
146
         return std::make_unique<CFB_Encryption>(std::move(bc), feedback_bits);
239✔
147
      else
148
         return std::make_unique<CFB_Decryption>(std::move(bc), feedback_bits);
160✔
149
   }
150
   #endif
151

152
#endif
153

154
   return std::unique_ptr<Cipher_Mode>();
8,142✔
155
}
8,184✔
156

157
//static
158
std::vector<std::string> Cipher_Mode::providers(std::string_view algo_spec) {
1,245✔
159
   const std::vector<std::string>& possible = {"base", "commoncrypto"};
3,735✔
160
   std::vector<std::string> providers;
1,245✔
161
   for(auto&& prov : possible) {
3,735✔
162
      auto mode = Cipher_Mode::create(algo_spec, Cipher_Dir::Encryption, prov);
2,490✔
163
      if(mode) {
2,490✔
164
         providers.push_back(prov);  // available
1,247✔
165
      }
166
   }
2,490✔
167
   return providers;
1,245✔
168
}
1,245✔
169

170
}
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

© 2025 Coveralls, Inc