• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 //
3 // Copyright 2022 gRPC authors.
4 //
5 // Licensed under the Apache License, Version 2.0 (the "License");
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 //     http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17 //
18 
19 #ifndef GRPC_SRC_CORE_TSI_SSL_TRANSPORT_SECURITY_UTILS_H
20 #define GRPC_SRC_CORE_TSI_SSL_TRANSPORT_SECURITY_UTILS_H
21 
22 #include <grpc/grpc_security_constants.h>
23 #include <grpc/support/port_platform.h>
24 #include <openssl/evp.h>
25 #include <openssl/x509.h>
26 
27 #include "absl/status/status.h"
28 #include "absl/status/statusor.h"
29 #include "absl/strings/string_view.h"
30 #include "src/core/tsi/ssl/key_logging/ssl_key_logging.h"
31 #include "src/core/tsi/transport_security_interface.h"
32 
33 namespace grpc_core {
34 
35 // Converts an SSL error status code to a readable string.
36 //
37 // error: the SSL error status code.
38 //
39 // return: the corresponding status string.
40 const char* SslErrorString(int error);
41 
42 // Logs the SSL error stack.
43 void LogSslErrorStack(void);
44 
45 // Performs an SSL_write and handle errors.
46 //
47 // ssl: the SSL object to write to.
48 // unprotected_bytes: the buffer containing the bytes for writing to |ssl|.
49 // unprotected_bytes_size: the size of the buffer |unprotected_bytes|.
50 //
51 // return: TSI_OK if the write operation succeeds or corresponding TSI errors.
52 tsi_result DoSslWrite(SSL* ssl, unsigned char* unprotected_bytes,
53                       size_t unprotected_bytes_size);
54 
55 // Performs an SSL_read and handle errors.
56 //
57 // ssl: the SSL object to read from.
58 // unprotected_bytes: the buffer to which this function will populate the read
59 //                    result from |ssl|.
60 // unprotected_bytes_size: the maximum size of the buffer |unprotected_bytes|.
61 //                         This will be populated with the size of the bytes
62 //                         read from |ssl| if this function returns TSI_OK.
63 //
64 // return: TSI_OK if the write operation succeeds or corresponding TSI errors.
65 tsi_result DoSslRead(SSL* ssl, unsigned char* unprotected_bytes,
66                      size_t* unprotected_bytes_size);
67 
68 // Builds a maximum-size TLS frame if there is enough (|buffer_offset| +
69 // |unprotected_bytes_size| >= |buffers_size|) data. Otherwise it copies the
70 // |unprotected_bytes| into |buffer| and returns TSI_OK.
71 //
72 // unprotected_bytes: pointing to the buffer containing the plaintext to be
73 //                    protected.
74 // buffer_size: the size of |buffer|. If |buffer_offset| equals |buffer_size|,
75 //              then we have enough data to create a TLS frame.
76 // buffer_offset: the offset of |buffer|. The data in |buffer| up to
77 //                |buffer_offset| are valid data. This will be updated whenever
78 //                new data are copied into |buffer|.
79 // buffer: the buffer holding the data that has not been sent for protecting.
80 // ssl: the |SSL| object that protects the data.
81 // network_io: the |BIO| object associated with |ssl|.
82 // unprotected_bytes_size: the size of the unprotected plaintext. This will be
83 //                         populated with the size of data that is consumed by
84 //                         this function. Caller can use this to see the size of
85 //                         unconsumed data in |unprotected_bytes|.
86 // protected_output_frames: the TLS frames built out of the plaintext.
87 // protected_output_frames_size: the size of the TLS frames built.
88 //
89 // return: TSI_OK if either successfully created a TSI frame or copied the
90 //         |unprotected_data| into |buffer|. Returns corresponding TSI errors
91 //         otherwise.
92 tsi_result SslProtectorProtect(const unsigned char* unprotected_bytes,
93                                const size_t buffer_size, size_t& buffer_offset,
94                                unsigned char* buffer, SSL* ssl, BIO* network_io,
95                                std::size_t* unprotected_bytes_size,
96                                unsigned char* protected_output_frames,
97                                size_t* protected_output_frames_size);
98 
99 // Builds a TLS frame out of the remaining plaintext bytes that's left in
100 // buffer. Populates the size of the remaining TLS frame to
101 // |still_pending_size|.
102 //
103 // buffer_size: the size of |buffer|. If |buffer_offset| equals |buffer_size|,
104 //              then we have enough data to create a TLS frame.
105 // buffer_offset: the offset of |buffer|. The data in |buffer| up to
106 //                |buffer_offset| are valid data. This will be updated whenever
107 //                new data are copied into |buffer|.
108 // buffer: the buffer holding the data that has not been sent for protecting.
109 // ssl: the |SSL| object that protects the data.
110 // network_io: the |BIO| object associated with |ssl|.
111 // protected_output_frames: the TLS frames built out of the plaintext.
112 // protected_output_frames_size: the size of the TLS frames built.
113 // still_pending_size: the size of the bytes that remains in |network_io|.
114 //
115 // return: TSI_OK if successfully created a TSI frame. Returns corresponding TSI
116 //         errors otherwise.
117 tsi_result SslProtectorProtectFlush(size_t& buffer_offset,
118                                     unsigned char* buffer, SSL* ssl,
119                                     BIO* network_io,
120                                     unsigned char* protected_output_frames,
121                                     size_t* protected_output_frames_size,
122                                     size_t* still_pending_size);
123 
124 // Extracts the plaintext from a TLS frame.
125 //
126 // protected_frames_bytes: the TLS frame to extract plaintext from.
127 // ssl: the |SSL| object that protects the data.
128 // network_io: the |BIO| object associated with |ssl|.
129 // unprotected_bytes_size: the size of the unprotected plaintext. This will be
130 //                         populated with the size of data that is consumed by
131 //                         this function. Caller can use this to see the size of
132 //                         unconsumed data in |unprotected_bytes|.
133 // protected_output_frames: the TLS frames built out of the plaintext.
134 // protected_output_frames_size: the size of the TLS frames built.
135 //
136 // return: TSI_OK if either successfully created a TSI frame or copied the
137 //         |unprotected_data| into |buffer|. Returns corresponding TSI errors
138 //         otherwise.
139 tsi_result SslProtectorUnprotect(const unsigned char* protected_frames_bytes,
140                                  SSL* ssl, BIO* network_io,
141                                  size_t* protected_frames_bytes_size,
142                                  unsigned char* unprotected_bytes,
143                                  size_t* unprotected_bytes_size);
144 
145 // Verifies that `crl` was signed by `issuer.
146 // return: true if valid, false otherwise.
147 bool VerifyCrlSignature(X509_CRL* crl, X509* issuer);
148 
149 // Verifies the CRL issuer and certificate issuer name match.
150 // return: true if equal, false if not.
151 bool VerifyCrlCertIssuerNamesMatch(X509_CRL* crl, X509* cert);
152 
153 // Verifies the certificate in question has the cRLSign bit present.
154 // return: true if cRLSign bit is present, false otherwise.
155 bool HasCrlSignBit(X509* cert);
156 
157 // Gets a stable representation of the issuer name from an X509 certificate.
158 // return: a std::string of the DER encoding of the X509_NAME issuer name.
159 absl::StatusOr<std::string> IssuerFromCert(X509* cert);
160 
161 // Gets a stable representation of the authority key identifier from an X509
162 // certificate.
163 // return: a std::string of the DER encoding of the AKID or a status on failure.
164 absl::StatusOr<std::string> AkidFromCertificate(X509* cert);
165 
166 // Gets a stable representation of the authority key identifier from an X509
167 // crl.
168 // return: a std::string of the DER encoding of the AKID or a status on failure.
169 absl::StatusOr<std::string> AkidFromCrl(X509_CRL* crl);
170 
171 // Returns a vector of X509 instances parsed from the given PEM-encoded
172 // certificate chain. Caller takes ownership of the X509 pointers in the output
173 // vector.
174 absl::StatusOr<std::vector<X509*>> ParsePemCertificateChain(
175     absl::string_view cert_chain_pem);
176 
177 // Returns an EVP_PKEY instance parsed from the non-empty PEM private key block
178 // in private_key_pem. Caller takes ownership of the EVP_PKEY pointer.
179 absl::StatusOr<EVP_PKEY*> ParsePemPrivateKey(absl::string_view private_key_pem);
180 }  // namespace grpc_core
181 
182 #endif  // GRPC_SRC_CORE_TSI_SSL_TRANSPORT_SECURITY_UTILS_H
183