1 // Copyright 2015 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 NET_DER_PARSE_VALUES_H_ 6 #define NET_DER_PARSE_VALUES_H_ 7 8 #include <stdint.h> 9 10 #include "net/base/net_export.h" 11 #include "net/der/input.h" 12 #include "third_party/abseil-cpp/absl/types/optional.h" 13 14 namespace net::der { 15 16 // Reads a DER-encoded ASN.1 BOOLEAN value from |in| and puts the resulting 17 // value in |out|. Returns whether the encoded value could successfully be 18 // read. 19 [[nodiscard]] NET_EXPORT bool ParseBool(const Input& in, bool* out); 20 21 // Like ParseBool, except it is more relaxed in what inputs it accepts: Any 22 // value that is a valid BER encoding will be parsed successfully. 23 [[nodiscard]] NET_EXPORT bool ParseBoolRelaxed(const Input& in, bool* out); 24 25 // Checks the validity of a DER-encoded ASN.1 INTEGER value from |in|, and 26 // determines the sign of the number. Returns true on success and 27 // fills |negative|. Otherwise returns false and does not modify the out 28 // parameter. 29 // 30 // in: The value portion of an INTEGER. 31 // negative: Out parameter that is set to true if the number is negative 32 // and false otherwise (zero is non-negative). 33 [[nodiscard]] NET_EXPORT bool IsValidInteger(const Input& in, bool* negative); 34 35 // Reads a DER-encoded ASN.1 INTEGER value from |in| and puts the resulting 36 // value in |out|. ASN.1 INTEGERs are arbitrary precision; this function is 37 // provided as a convenience when the caller knows that the value is unsigned 38 // and is between 0 and 2^64-1. This function returns false if the value is too 39 // big to fit in a uint64_t, is negative, or if there is an error reading the 40 // integer. 41 [[nodiscard]] NET_EXPORT bool ParseUint64(const Input& in, uint64_t* out); 42 43 // Same as ParseUint64() but for a uint8_t. 44 [[nodiscard]] NET_EXPORT bool ParseUint8(const Input& in, uint8_t* out); 45 46 // The BitString class is a helper for representing a valid parsed BIT STRING. 47 // 48 // * The bits are ordered within each octet of bytes() from most to least 49 // significant, as in the DER encoding. 50 // 51 // * There may be at most 7 unused bits. 52 class NET_EXPORT BitString { 53 public: 54 BitString() = default; 55 56 // |unused_bits| represents the number of bits in the last octet of |bytes|, 57 // starting from the least significant bit, that are unused. It MUST be < 8. 58 // And if bytes is empty, then it MUST be 0. 59 BitString(const Input& bytes, uint8_t unused_bits); 60 bytes()61 const Input& bytes() const { return bytes_; } unused_bits()62 uint8_t unused_bits() const { return unused_bits_; } 63 64 // Returns true if the bit string contains 1 at the specified position. 65 // Otherwise returns false. 66 // 67 // A return value of false can mean either: 68 // * The bit value at |bit_index| is 0. 69 // * There is no bit at |bit_index| (index is beyond the end). 70 [[nodiscard]] bool AssertsBit(size_t bit_index) const; 71 72 private: 73 Input bytes_; 74 uint8_t unused_bits_ = 0; 75 76 // Default assignment and copy constructor are OK. 77 }; 78 79 // Reads a DER-encoded ASN.1 BIT STRING value from |in| and returns the 80 // resulting octet string and number of unused bits. 81 // 82 // On failure, returns absl::nullopt. 83 [[nodiscard]] NET_EXPORT absl::optional<BitString> ParseBitString( 84 const Input& in); 85 86 struct NET_EXPORT GeneralizedTime { 87 uint16_t year; 88 uint8_t month; 89 uint8_t day; 90 uint8_t hours; 91 uint8_t minutes; 92 uint8_t seconds; 93 94 // Returns true if the value is in UTCTime's range. 95 bool InUTCTimeRange() const; 96 }; 97 98 NET_EXPORT_PRIVATE bool operator<(const GeneralizedTime& lhs, 99 const GeneralizedTime& rhs); 100 NET_EXPORT_PRIVATE bool operator<=(const GeneralizedTime& lhs, 101 const GeneralizedTime& rhs); 102 NET_EXPORT_PRIVATE bool operator>(const GeneralizedTime& lhs, 103 const GeneralizedTime& rhs); 104 NET_EXPORT_PRIVATE bool operator>=(const GeneralizedTime& lhs, 105 const GeneralizedTime& rhs); 106 107 // Reads a DER-encoded ASN.1 UTCTime value from |in| and puts the resulting 108 // value in |out|, returning true if the UTCTime could be parsed successfully. 109 [[nodiscard]] NET_EXPORT bool ParseUTCTime(const Input& in, 110 GeneralizedTime* out); 111 112 // Reads a DER-encoded ASN.1 GeneralizedTime value from |in| and puts the 113 // resulting value in |out|, returning true if the GeneralizedTime could 114 // be parsed successfully. This function is even more restrictive than the 115 // DER rules - it follows the rules from RFC5280, which does not allow for 116 // fractional seconds. 117 [[nodiscard]] NET_EXPORT bool ParseGeneralizedTime(const Input& in, 118 GeneralizedTime* out); 119 120 // Reads a DER-encoded ASN.1 IA5String value from |in| and stores the result in 121 // |out| as ASCII, returning true if successful. 122 [[nodiscard]] NET_EXPORT bool ParseIA5String(Input in, std::string* out); 123 124 // Reads a DER-encoded ASN.1 VisibleString value from |in| and stores the result 125 // in |out| as ASCII, returning true if successful. 126 [[nodiscard]] NET_EXPORT bool ParseVisibleString(Input in, std::string* out); 127 128 // Reads a DER-encoded ASN.1 PrintableString value from |in| and stores the 129 // result in |out| as ASCII, returning true if successful. 130 [[nodiscard]] NET_EXPORT bool ParsePrintableString(Input in, std::string* out); 131 132 // Reads a DER-encoded ASN.1 TeletexString value from |in|, treating it as 133 // Latin-1, and stores the result in |out| as UTF-8, returning true if 134 // successful. 135 // 136 // This is for compatibility with legacy implementations that would use Latin-1 137 // encoding but tag it as TeletexString. 138 [[nodiscard]] NET_EXPORT bool ParseTeletexStringAsLatin1(Input in, 139 std::string* out); 140 141 // Reads a DER-encoded ASN.1 UniversalString value from |in| and stores the 142 // result in |out| as UTF-8, returning true if successful. 143 [[nodiscard]] NET_EXPORT bool ParseUniversalString(Input in, std::string* out); 144 145 // Reads a DER-encoded ASN.1 BMPString value from |in| and stores the 146 // result in |out| as UTF-8, returning true if successful. 147 [[nodiscard]] NET_EXPORT bool ParseBmpString(Input in, std::string* out); 148 149 } // namespace net::der 150 151 #endif // NET_DER_PARSE_VALUES_H_ 152