Loading src/crypto/cert_verify.cpp +21 −1 Original line number Diff line number Diff line #include "cert_verify.h" #include "cert_verify_platform.h" #include <ctime> #include <fstream> #include <mutex> #include <unordered_map> Loading Loading @@ -75,7 +76,26 @@ void verifyPeerChain(const std::vector<std::vector<uint8_t>> &presentedDerCerts, x509cert leaf; if (!leaf.loadFromBuffer(presentedDerCerts[0])) fail("could not parse leaf certificate"); if (!leaf.checkValidity()) fail("leaf certificate is expired or not yet valid"); if (!leaf.checkValidity()) { // which way: an expired certificate, or this system's clock auto utc = [](time_t t) { if (!t) return std::string("?"); struct tm tmv; #ifdef _WIN32 gmtime_s(&tmv, &t); #else gmtime_r(&t, &tmv); #endif char buf[32]; strftime(buf, sizeof buf, "%Y-%m-%d %H:%M:%SZ", &tmv); return std::string(buf); }; time_t now = time(nullptr), nb = leaf.getNotBefore(), na = leaf.getNotAfter(); std::string why = na && now > na ? "leaf certificate expired" : nb && now < nb ? "leaf certificate not yet valid" : "leaf certificate validity unreadable"; fail(why + " (valid " + utc(nb) + " to " + utc(na) + ", this system's clock: " + utc(now) + ")"); } if (!policy.expectedHostname.empty() && !leaf.matchesHostname(policy.expectedHostname)) fail("hostname mismatch (expected " + policy.expectedHostname + ")"); Loading src/crypto/x509.cpp +20 −0 Original line number Diff line number Diff line Loading @@ -401,6 +401,26 @@ time_t netplus::x509cert::getNotAfter() { return parseASN1Time(na.data, na.len, na.tag); } // ------------------------------------------------------------ // getNotBefore -- the notBefore time_t, 0 if there is none // ------------------------------------------------------------ time_t netplus::x509cert::getNotBefore() { auto& r = root(); if (r.children.empty() || r.children[0].children.size() < 5) return 0; for (auto& node : r.children[0].children) { if (node.tag == 0x30 && node.children.size() >= 2) { uint8_t t1 = node.children[0].tag; uint8_t t2 = node.children[1].tag; if ((t1 == 0x17 || t1 == 0x18) && (t2 == 0x17 || t2 == 0x18)) { const ASN1Node& nb = node.children[0]; return parseASN1Time(nb.data, nb.len, nb.tag); } } } return 0; } // ------------------------------------------------------------ // bytesToBigInt -- vector-based (keeps header compat) // ------------------------------------------------------------ Loading src/crypto/x509.h +1 −0 Original line number Diff line number Diff line Loading @@ -69,6 +69,7 @@ namespace netplus { bool checkValidity(); time_t getNotAfter(); time_t getNotBefore(); bool extractPublicKey(netplus::rsa& outRsa); bool isECKey() const; bool extractECPublicKey(std::vector<uint8_t>& outPubRaw); Loading Loading
src/crypto/cert_verify.cpp +21 −1 Original line number Diff line number Diff line #include "cert_verify.h" #include "cert_verify_platform.h" #include <ctime> #include <fstream> #include <mutex> #include <unordered_map> Loading Loading @@ -75,7 +76,26 @@ void verifyPeerChain(const std::vector<std::vector<uint8_t>> &presentedDerCerts, x509cert leaf; if (!leaf.loadFromBuffer(presentedDerCerts[0])) fail("could not parse leaf certificate"); if (!leaf.checkValidity()) fail("leaf certificate is expired or not yet valid"); if (!leaf.checkValidity()) { // which way: an expired certificate, or this system's clock auto utc = [](time_t t) { if (!t) return std::string("?"); struct tm tmv; #ifdef _WIN32 gmtime_s(&tmv, &t); #else gmtime_r(&t, &tmv); #endif char buf[32]; strftime(buf, sizeof buf, "%Y-%m-%d %H:%M:%SZ", &tmv); return std::string(buf); }; time_t now = time(nullptr), nb = leaf.getNotBefore(), na = leaf.getNotAfter(); std::string why = na && now > na ? "leaf certificate expired" : nb && now < nb ? "leaf certificate not yet valid" : "leaf certificate validity unreadable"; fail(why + " (valid " + utc(nb) + " to " + utc(na) + ", this system's clock: " + utc(now) + ")"); } if (!policy.expectedHostname.empty() && !leaf.matchesHostname(policy.expectedHostname)) fail("hostname mismatch (expected " + policy.expectedHostname + ")"); Loading
src/crypto/x509.cpp +20 −0 Original line number Diff line number Diff line Loading @@ -401,6 +401,26 @@ time_t netplus::x509cert::getNotAfter() { return parseASN1Time(na.data, na.len, na.tag); } // ------------------------------------------------------------ // getNotBefore -- the notBefore time_t, 0 if there is none // ------------------------------------------------------------ time_t netplus::x509cert::getNotBefore() { auto& r = root(); if (r.children.empty() || r.children[0].children.size() < 5) return 0; for (auto& node : r.children[0].children) { if (node.tag == 0x30 && node.children.size() >= 2) { uint8_t t1 = node.children[0].tag; uint8_t t2 = node.children[1].tag; if ((t1 == 0x17 || t1 == 0x18) && (t2 == 0x17 || t2 == 0x18)) { const ASN1Node& nb = node.children[0]; return parseASN1Time(nb.data, nb.len, nb.tag); } } } return 0; } // ------------------------------------------------------------ // bytesToBigInt -- vector-based (keeps header compat) // ------------------------------------------------------------ Loading
src/crypto/x509.h +1 −0 Original line number Diff line number Diff line Loading @@ -69,6 +69,7 @@ namespace netplus { bool checkValidity(); time_t getNotAfter(); time_t getNotBefore(); bool extractPublicKey(netplus::rsa& outRsa); bool isECKey() const; bool extractECPublicKey(std::vector<uint8_t>& outPubRaw); Loading