• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2011 The Chromium Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef BSSL_PKI_PEM_H_
6 #define BSSL_PKI_PEM_H_
7 
8 #include "fillins/openssl_util.h"
9 #include <stddef.h>
10 
11 #include <string>
12 #include <vector>
13 
14 #include <string_view>
15 
16 
17 
18 namespace bssl {
19 
20 // PEMTokenizer is a utility class for the parsing of data encapsulated
21 // using RFC 1421, Privacy Enhancement for Internet Electronic Mail. It
22 // does not implement the full specification, most notably it does not
23 // support the Encapsulated Header Portion described in Section 4.4.
24 class OPENSSL_EXPORT PEMTokenizer {
25  public:
26   // Create a new PEMTokenizer that iterates through |str| searching for
27   // instances of PEM encoded blocks that are of the |allowed_block_types|.
28   // |str| must remain valid for the duration of the PEMTokenizer.
29   PEMTokenizer(std::string_view str,
30                const std::vector<std::string>& allowed_block_types);
31 
32   PEMTokenizer(const PEMTokenizer&) = delete;
33   PEMTokenizer& operator=(const PEMTokenizer&) = delete;
34 
35   ~PEMTokenizer();
36 
37   // Attempts to decode the next PEM block in the string. Returns false if no
38   // PEM blocks can be decoded. The decoded PEM block will be available via
39   // data().
40   bool GetNext();
41 
42   // Returns the PEM block type (eg: CERTIFICATE) of the last successfully
43   // decoded PEM block.
44   // GetNext() must have returned true before calling this method.
block_type()45   const std::string& block_type() const { return block_type_; }
46 
47   // Returns the raw, Base64-decoded data of the last successfully decoded
48   // PEM block.
49   // GetNext() must have returned true before calling this method.
data()50   const std::string& data() const { return data_; }
51 
52  private:
53   void Init(std::string_view str,
54             const std::vector<std::string>& allowed_block_types);
55 
56   // A simple cache of the allowed PEM header and footer for a given PEM
57   // block type, so that it is only computed once.
58   struct PEMType;
59 
60   // The string to search, which must remain valid for as long as this class
61   // is around.
62   std::string_view str_;
63 
64   // The current position within |str_| that searching should begin from,
65   // or std::string_view::npos if iteration is complete
66   std::string_view::size_type pos_;
67 
68   // The type of data that was encoded, as indicated in the PEM
69   // Pre-Encapsulation Boundary (eg: CERTIFICATE, PKCS7, or
70   // PRIVACY-ENHANCED MESSAGE).
71   std::string block_type_;
72 
73   // The types of PEM blocks that are allowed. PEM blocks that are not of
74   // one of these types will be skipped.
75   std::vector<PEMType> block_types_;
76 
77   // The raw (Base64-decoded) data of the last successfully decoded block.
78   std::string data_;
79 };
80 
81 // Encodes |data| in the encapsulated message format described in RFC 1421,
82 // with |type| as the PEM block type (eg: CERTIFICATE).
83 OPENSSL_EXPORT std::string PEMEncode(std::string_view data,
84                                          const std::string& type);
85 
86 }  // namespace net
87 
88 #endif  // BSSL_PKI_PEM_H_
89