1984 | 1984 |
// Report certificate weaknesses (key length and signing algorithm)
|
1985 | 1985 |
int checkCertificate(struct sslCheckOptions *options, const SSL_METHOD *sslMethod)
|
1986 | 1986 |
{
|
1987 | |
int cipherStatus = 0;
|
1988 | 1987 |
int status = true;
|
1989 | 1988 |
int socketDescriptor = 0;
|
1990 | 1989 |
int keyBits;
|
|
2042 | 2041 |
#endif
|
2043 | 2042 |
|
2044 | 2043 |
// Connect SSL over socket
|
2045 | |
cipherStatus = SSL_connect(ssl);
|
2046 | |
if (cipherStatus == 1)
|
|
2044 |
SSL_connect(ssl);
|
|
2045 |
// Setup BIO's
|
|
2046 |
if (!xml_to_stdout) {
|
|
2047 |
stdoutBIO = BIO_new(BIO_s_file());
|
|
2048 |
BIO_set_fp(stdoutBIO, stdout, BIO_NOCLOSE);
|
|
2049 |
}
|
|
2050 |
if (options->xmlOutput)
|
2047 | 2051 |
{
|
2048 | |
// Setup BIO's
|
2049 | |
if (!xml_to_stdout) {
|
2050 | |
stdoutBIO = BIO_new(BIO_s_file());
|
2051 | |
BIO_set_fp(stdoutBIO, stdout, BIO_NOCLOSE);
|
2052 | |
}
|
2053 | |
if (options->xmlOutput)
|
2054 | |
{
|
2055 | |
fileBIO = BIO_new(BIO_s_file());
|
2056 | |
BIO_set_fp(fileBIO, options->xmlOutput, BIO_NOCLOSE);
|
2057 | |
}
|
2058 | |
|
2059 | |
// Get Certificate...
|
|
2052 |
fileBIO = BIO_new(BIO_s_file());
|
|
2053 |
BIO_set_fp(fileBIO, options->xmlOutput, BIO_NOCLOSE);
|
|
2054 |
}
|
|
2055 |
|
|
2056 |
// Get Certificate...
|
|
2057 |
x509Cert = SSL_get_peer_certificate(ssl);
|
|
2058 |
if (x509Cert != NULL)
|
|
2059 |
{
|
2060 | 2060 |
printf("\n %sSSL Certificate:%s\n", COL_BLUE, RESET);
|
2061 | 2061 |
printf_xml(" <certificate type=\"short\">\n");
|
2062 | |
x509Cert = SSL_get_peer_certificate(ssl);
|
2063 | |
if (x509Cert != NULL)
|
|
2062 |
// Cert Serial No. - Code adapted from OpenSSL's crypto/asn1/t_x509.c
|
|
2063 |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_SERIAL))
|
2064 | 2064 |
{
|
2065 | |
// Cert Serial No. - Code adapted from OpenSSL's crypto/asn1/t_x509.c
|
2066 | |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_SERIAL))
|
2067 | |
{
|
2068 | |
BIO *bp;
|
2069 | |
bp = BIO_new_fp(stdout, BIO_NOCLOSE);
|
2070 | |
if (options->xmlOutput)
|
|
2065 |
BIO *bp;
|
|
2066 |
bp = BIO_new_fp(stdout, BIO_NOCLOSE);
|
|
2067 |
if (options->xmlOutput)
|
2071 | 2068 |
|
2072 | 2069 |
if(NULL != bp)
|
2073 | 2070 |
BIO_free(bp);
|
2074 | |
// We don't free the xml_bp because it will be used in the future
|
|
2071 |
// We don't free the xml_bp because it will be used in the future
|
|
2072 |
}
|
|
2073 |
|
|
2074 |
// Signature Algo...
|
|
2075 |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_SIGNAME))
|
|
2076 |
{
|
|
2077 |
printf("Signature Algorithm: ");
|
|
2078 |
X509_get0_signature(NULL, &palg, x509Cert);
|
|
2079 |
X509_ALGOR_get0(&paobj, NULL, NULL, palg);
|
|
2080 |
OBJ_obj2txt(certAlgorithm, sizeof(certAlgorithm), paobj, 0);
|
|
2081 |
strtok(certAlgorithm, "\n");
|
|
2082 |
if (strstr(certAlgorithm, "md5") || strstr(certAlgorithm, "sha1"))
|
|
2083 |
{
|
|
2084 |
printf("%s%s%s\n", COL_RED, certAlgorithm, RESET);
|
2075 | 2085 |
}
|
2076 | |
|
2077 | |
// Signature Algo...
|
2078 | |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_SIGNAME))
|
|
2086 |
else if (strstr(certAlgorithm, "sha512") || strstr(certAlgorithm, "sha256"))
|
2079 | 2087 |
{
|
2080 | |
printf("Signature Algorithm: ");
|
2081 | |
X509_get0_signature(NULL, &palg, x509Cert);
|
2082 | |
X509_ALGOR_get0(&paobj, NULL, NULL, palg);
|
2083 | |
OBJ_obj2txt(certAlgorithm, sizeof(certAlgorithm), paobj, 0);
|
2084 | |
strtok(certAlgorithm, "\n");
|
2085 | |
if (strstr(certAlgorithm, "md5") || strstr(certAlgorithm, "sha1"))
|
|
2088 |
printf("%s%s%s\n", COL_GREEN, certAlgorithm, RESET);
|
|
2089 |
}
|
|
2090 |
else
|
|
2091 |
{
|
|
2092 |
printf("%s\n", certAlgorithm);
|
|
2093 |
}
|
|
2094 |
|
|
2095 |
if (options->xmlOutput)
|
|
2096 |
{
|
|
2097 |
printf_xml(" <signature-algorithm>%s</signature-algorithm>\n", certAlgorithm);
|
|
2098 |
}
|
|
2099 |
}
|
|
2100 |
|
|
2101 |
// Public Key...
|
|
2102 |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_PUBKEY))
|
|
2103 |
{
|
|
2104 |
publicKey = X509_get_pubkey(x509Cert);
|
|
2105 |
if (publicKey == NULL)
|
|
2106 |
{
|
|
2107 |
printf("Public Key: Could not load\n");
|
|
2108 |
printf_xml(" <pk error=\"true\" />\n");
|
|
2109 |
}
|
|
2110 |
else
|
|
2111 |
{
|
|
2112 |
keyBits=EVP_PKEY_bits(publicKey);
|
|
2113 |
switch (EVP_PKEY_id(publicKey))
|
2086 | 2114 |
{
|
2087 | |
printf("%s%s%s\n", COL_RED, certAlgorithm, RESET);
|
2088 | |
}
|
2089 | |
else if (strstr(certAlgorithm, "sha512") || strstr(certAlgorithm, "sha256"))
|
2090 | |
{
|
2091 | |
printf("%s%s%s\n", COL_GREEN, certAlgorithm, RESET);
|
2092 | |
}
|
2093 | |
else
|
2094 | |
{
|
2095 | |
printf("%s\n", certAlgorithm);
|
2096 | |
}
|
2097 | |
|
2098 | |
if (options->xmlOutput)
|
2099 | |
{
|
2100 | |
printf_xml(" <signature-algorithm>%s</signature-algorithm>\n", certAlgorithm);
|
2101 | |
}
|
2102 | |
}
|
2103 | |
|
2104 | |
// Public Key...
|
2105 | |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_PUBKEY))
|
2106 | |
{
|
2107 | |
publicKey = X509_get_pubkey(x509Cert);
|
2108 | |
if (publicKey == NULL)
|
2109 | |
{
|
2110 | |
printf("Public Key: Could not load\n");
|
2111 | |
printf_xml(" <pk error=\"true\" />\n");
|
2112 | |
}
|
2113 | |
else
|
2114 | |
{
|
2115 | |
keyBits=EVP_PKEY_bits(publicKey);
|
2116 | |
switch (EVP_PKEY_id(publicKey))
|
2117 | |
{
|
2118 | |
case EVP_PKEY_RSA:
|
2119 | |
if (EVP_PKEY_get1_RSA(publicKey)!=NULL)
|
|
2115 |
case EVP_PKEY_RSA:
|
|
2116 |
if (EVP_PKEY_get1_RSA(publicKey)!=NULL)
|
|
2117 |
{
|
|
2118 |
if (keyBits < 2048 )
|
2120 | 2119 |
{
|
2121 | |
if (keyBits < 2048 )
|
2122 | |
{
|
2123 | |
printf("RSA Key Strength: %s%d%s\n", COL_RED, keyBits, RESET);
|
2124 | |
}
|
2125 | |
else if (keyBits >= 3072 )
|
2126 | |
{
|
2127 | |
printf("RSA Key Strength: %s%d%s\n", COL_GREEN, keyBits, RESET);
|
2128 | |
}
|
2129 | |
else
|
2130 | |
{
|
2131 | |
printf("RSA Key Strength: %d\n", keyBits);
|
2132 | |
}
|
2133 | |
|
2134 | |
printf_xml(" <pk error=\"false\" type=\"RSA\" bits=\"%d\" />\n", keyBits);
|
|
2120 |
printf("RSA Key Strength: %s%d%s\n", COL_RED, keyBits, RESET);
|
|
2121 |
}
|
|
2122 |
else if (keyBits >= 3072 )
|
|
2123 |
{
|
|
2124 |
printf("RSA Key Strength: %s%d%s\n", COL_GREEN, keyBits, RESET);
|
2135 | 2125 |
}
|
2136 | 2126 |
else
|
2137 | 2127 |
{
|
2138 | |
printf(" RSA Public Key: NULL\n");
|
|
2128 |
printf("RSA Key Strength: %d\n", keyBits);
|
2139 | 2129 |
}
|
2140 | |
printf("\n");
|
2141 | |
break;
|
2142 | |
case EVP_PKEY_DSA:
|
2143 | |
if (EVP_PKEY_get1_DSA(publicKey)!=NULL)
|
|
2130 |
|
|
2131 |
printf_xml(" <pk error=\"false\" type=\"RSA\" bits=\"%d\" />\n", keyBits);
|
|
2132 |
}
|
|
2133 |
else
|
|
2134 |
{
|
|
2135 |
printf(" RSA Public Key: NULL\n");
|
|
2136 |
}
|
|
2137 |
printf("\n");
|
|
2138 |
break;
|
|
2139 |
case EVP_PKEY_DSA:
|
|
2140 |
if (EVP_PKEY_get1_DSA(publicKey)!=NULL)
|
|
2141 |
{
|
|
2142 |
// TODO - display key strength
|
|
2143 |
printf_xml(" <pk error=\"false\" type=\"DSA\" />\n");
|
|
2144 |
/* DSA_print(stdoutBIO, publicKey->pkey.dsa, 6); */
|
|
2145 |
}
|
|
2146 |
else
|
|
2147 |
{
|
|
2148 |
printf(" DSA Public Key: NULL\n");
|
|
2149 |
}
|
|
2150 |
break;
|
|
2151 |
case EVP_PKEY_EC:
|
|
2152 |
{
|
|
2153 |
EC_KEY *ec_key = EVP_PKEY_get1_EC_KEY(publicKey);
|
|
2154 |
if (ec_key != NULL)
|
2144 | 2155 |
{
|
2145 | |
// TODO - display key strength
|
2146 | |
printf_xml(" <pk error=\"false\" type=\"DSA\" />\n");
|
2147 | |
/* DSA_print(stdoutBIO, publicKey->pkey.dsa, 6); */
|
2148 | |
}
|
2149 | |
else
|
2150 | |
{
|
2151 | |
printf(" DSA Public Key: NULL\n");
|
2152 | |
}
|
2153 | |
break;
|
2154 | |
case EVP_PKEY_EC:
|
2155 | |
{
|
2156 | |
EC_KEY *ec_key = EVP_PKEY_get1_EC_KEY(publicKey);
|
2157 | |
if (ec_key != NULL)
|
2158 | |
{
|
2159 | 2156 |
// We divide by two to get the symmetric key strength equivalent; this
|
2160 | 2157 |
// ensures consistency with the Server Key Exchange Group section.
|
2161 | 2158 |
int keyBits = EVP_PKEY_bits(publicKey) / 2;
|
|
2164 | 2161 |
|
2165 | 2162 |
|
2166 | 2163 |
if (keyBits < 112)
|
2167 | |
color = COL_RED;
|
|
2164 |
color = COL_RED;
|
2168 | 2165 |
else if (keyBits < 128)
|
2169 | |
color = COL_YELLOW;
|
|
2166 |
color = COL_YELLOW;
|
2170 | 2167 |
|
2171 | 2168 |
printf("ECC Curve Name: %s\n", ec_group_name);
|
2172 | 2169 |
printf("ECC Key Strength: %s%d%s\n\n", color, keyBits, RESET);
|
2173 | 2170 |
printf_xml(" <pk error=\"false\" type=\"EC\" curve_name=\"%s\" bits=\"%d\" />\n", ec_group_name, keyBits);
|
2174 | 2171 |
EC_KEY_free(ec_key); ec_key = NULL;
|
2175 | |
}
|
2176 | |
else
|
|
2172 |
}
|
|
2173 |
else
|
2177 | 2174 |
printf(" EC Public Key: NULL\n");
|
2178 | |
}
|
2179 | |
break;
|
2180 | |
default:
|
2181 | |
printf(" Public Key: Unknown\n");
|
2182 | |
printf_xml(" <pk error=\"true\" type=\"unknown\" />\n");
|
2183 | |
break;
|
|
2175 |
}
|
|
2176 |
break;
|
|
2177 |
default:
|
|
2178 |
printf(" Public Key: Unknown\n");
|
|
2179 |
printf_xml(" <pk error=\"true\" type=\"unknown\" />\n");
|
|
2180 |
break;
|
|
2181 |
}
|
|
2182 |
|
|
2183 |
EVP_PKEY_free(publicKey);
|
|
2184 |
}
|
|
2185 |
}
|
|
2186 |
|
|
2187 |
// SSL Certificate Issuer...
|
|
2188 |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_ISSUER))
|
|
2189 |
{
|
|
2190 |
int cnindex;
|
|
2191 |
X509_NAME *subj;
|
|
2192 |
X509_NAME_ENTRY *e;
|
|
2193 |
ASN1_STRING *d;
|
|
2194 |
const char *subject;
|
|
2195 |
const char *issuer;
|
|
2196 |
|
|
2197 |
// Get SSL cert CN
|
|
2198 |
cnindex = -1;
|
|
2199 |
subj = X509_get_subject_name(x509Cert);
|
|
2200 |
cnindex = X509_NAME_get_index_by_NID(subj, NID_commonName, cnindex);
|
|
2201 |
|
|
2202 |
// SSL cert doesn't have a CN, so just print whole thing
|
|
2203 |
if (cnindex == -1)
|
|
2204 |
{
|
|
2205 |
subject = (char *) X509_NAME_oneline(X509_get_subject_name(x509Cert), NULL, 0);
|
|
2206 |
printf("Subject: %s\n", subject);
|
|
2207 |
printf_xml(" <subject><![CDATA[%s]]></subject>\n", subject);
|
|
2208 |
|
|
2209 |
}
|
|
2210 |
else
|
|
2211 |
{
|
|
2212 |
e = X509_NAME_get_entry(subj, cnindex);
|
|
2213 |
d = X509_NAME_ENTRY_get_data(e);
|
|
2214 |
subject = (char *) ASN1_STRING_data(d);
|
|
2215 |
printf("Subject: %s\n", subject);
|
|
2216 |
printf_xml(" <subject><![CDATA[%s]]></subject>\n", subject);
|
|
2217 |
}
|
|
2218 |
|
|
2219 |
// Get certificate altnames if supported
|
|
2220 |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_EXTENSIONS))
|
|
2221 |
{
|
|
2222 |
if (sk_X509_EXTENSION_num(X509_get0_extensions(x509Cert)) > 0)
|
|
2223 |
{
|
|
2224 |
cnindex = X509_get_ext_by_NID (x509Cert, NID_subject_alt_name, -1);
|
|
2225 |
if (cnindex != -1)
|
|
2226 |
{
|
|
2227 |
extension = X509v3_get_ext(X509_get0_extensions(x509Cert),cnindex);
|
|
2228 |
|
|
2229 |
printf("Altnames: ");
|
|
2230 |
if (!X509V3_EXT_print(stdoutBIO, extension, X509_FLAG_COMPAT, 0))
|
|
2231 |
{
|
|
2232 |
ASN1_STRING_print(stdoutBIO, X509_EXTENSION_get_data(extension));
|
|
2233 |
}
|
|
2234 |
if (options->xmlOutput)
|
|
2235 |
{
|
|
2236 |
printf_xml(" <altnames><![CDATA[");
|
|
2237 |
if (!X509V3_EXT_print(fileBIO, extension, X509_FLAG_COMPAT, 0))
|
|
2238 |
ASN1_STRING_print(fileBIO, X509_EXTENSION_get_data(extension));
|
|
2239 |
}
|
|
2240 |
printf_xml("]]></altnames>\n");
|
|
2241 |
printf("\n");
|
2184 | 2242 |
}
|
2185 | |
|
2186 | |
EVP_PKEY_free(publicKey);
|
2187 | 2243 |
}
|
2188 | 2244 |
}
|
2189 | 2245 |
|
2190 | |
// SSL Certificate Issuer...
|
2191 | |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_ISSUER))
|
|
2246 |
// Get SSL cert issuer
|
|
2247 |
cnindex = -1;
|
|
2248 |
subj = X509_get_issuer_name(x509Cert);
|
|
2249 |
cnindex = X509_NAME_get_index_by_NID(subj, NID_commonName, cnindex);
|
|
2250 |
|
|
2251 |
// Issuer cert doesn't have a CN, so just print whole thing
|
|
2252 |
if (cnindex == -1)
|
2192 | 2253 |
{
|
2193 | |
int cnindex;
|
2194 | |
X509_NAME *subj;
|
2195 | |
X509_NAME_ENTRY *e;
|
2196 | |
ASN1_STRING *d;
|
2197 | |
const char *subject;
|
2198 | |
const char *issuer;
|
2199 | |
|
2200 | |
// Get SSL cert CN
|
2201 | |
cnindex = -1;
|
2202 | |
subj = X509_get_subject_name(x509Cert);
|
2203 | |
cnindex = X509_NAME_get_index_by_NID(subj, NID_commonName, cnindex);
|
2204 | |
|
2205 | |
// SSL cert doesn't have a CN, so just print whole thing
|
2206 | |
if (cnindex == -1)
|
|
2254 |
char *issuer = X509_NAME_oneline(X509_get_issuer_name(x509Cert), NULL, 0);
|
|
2255 |
char *color = "";
|
|
2256 |
int self_signed = 0;
|
|
2257 |
|
|
2258 |
if ((subject != NULL) && (strcmp(subject, issuer) == 0)) {
|
|
2259 |
color = COL_RED;
|
|
2260 |
self_signed = 1;
|
|
2261 |
}
|
|
2262 |
printf("%sIssuer: %s%s", color, issuer, RESET);
|
|
2263 |
printf_xml(" <issuer><![CDATA[%s]]></issuer>\n", issuer);
|
|
2264 |
|
|
2265 |
if (self_signed) {
|
|
2266 |
printf_xml(" <self-signed>true</self-signed>\n");
|
|
2267 |
}
|
|
2268 |
else {
|
|
2269 |
printf_xml(" <self-signed>false</self-signed>\n");
|
|
2270 |
}
|
|
2271 |
}
|
|
2272 |
else
|
|
2273 |
{
|
|
2274 |
e = X509_NAME_get_entry(subj, cnindex);
|
|
2275 |
d = X509_NAME_ENTRY_get_data(e);
|
|
2276 |
issuer = (char *) ASN1_STRING_data(d);
|
|
2277 |
|
|
2278 |
// If issuer is same as hostname we scanned or is *, flag as self-signed
|
|
2279 |
if (
|
|
2280 |
strcmp(issuer, options->host) == 0
|
|
2281 |
|| strcmp(issuer, subject) == 0
|
|
2282 |
|| strcmp(issuer, "*") == 0
|
|
2283 |
)
|
2207 | 2284 |
{
|
2208 | |
subject = (char *) X509_NAME_oneline(X509_get_subject_name(x509Cert), NULL, 0);
|
2209 | |
printf("Subject: %s\n", subject);
|
2210 | |
printf_xml(" <subject><![CDATA[%s]]></subject>\n", subject);
|
|
2285 |
printf("Issuer: %s%s%s\n", COL_RED, issuer, RESET);
|
|
2286 |
printf_xml(" <issuer><![CDATA[%s]]></issuer>\n", issuer);
|
|
2287 |
printf_xml(" <self-signed>true</self-signed>\n");
|
2211 | 2288 |
|
2212 | 2289 |
}
|
2213 | 2290 |
else
|
2214 | 2291 |
{
|
2215 | |
e = X509_NAME_get_entry(subj, cnindex);
|
2216 | |
d = X509_NAME_ENTRY_get_data(e);
|
2217 | |
subject = (char *) ASN1_STRING_data(d);
|
2218 | |
printf("Subject: %s\n", subject);
|
2219 | |
printf_xml(" <subject><![CDATA[%s]]></subject>\n", subject);
|
2220 | |
}
|
2221 | |
|
2222 | |
// Get certificate altnames if supported
|
2223 | |
if (!(X509_FLAG_COMPAT & X509_FLAG_NO_EXTENSIONS))
|
2224 | |
{
|
2225 | |
if (sk_X509_EXTENSION_num(X509_get0_extensions(x509Cert)) > 0)
|
2226 | |
{
|
2227 | |
cnindex = X509_get_ext_by_NID (x509Cert, NID_subject_alt_name, -1);
|
2228 | |
if (cnindex != -1)
|
2229 | |
{
|
2230 | |
extension = X509v3_get_ext(X509_get0_extensions(x509Cert),cnindex);
|
2231 | |
|
2232 | |
printf("Altnames: ");
|
2233 | |
if (!X509V3_EXT_print(stdoutBIO, extension, X509_FLAG_COMPAT, 0))
|
2234 | |
{
|
2235 | |
ASN1_STRING_print(stdoutBIO, X509_EXTENSION_get_data(extension));
|
2236 | |
}
|
2237 | |
if (options->xmlOutput)
|
2238 | |
{
|
2239 | |
printf_xml(" <altnames><![CDATA[");
|
2240 | |
if (!X509V3_EXT_print(fileBIO, extension, X509_FLAG_COMPAT, 0))
|
2241 | |
ASN1_STRING_print(fileBIO, X509_EXTENSION_get_data(extension));
|
2242 | |
}
|
2243 | |
printf_xml("]]></altnames>\n");
|
2244 | |
printf("\n");
|
2245 | |
}
|
2246 | |
}
|
2247 | |
}
|
2248 | |
|
2249 | |
// Get SSL cert issuer
|
2250 | |
cnindex = -1;
|
2251 | |
subj = X509_get_issuer_name(x509Cert);
|
2252 | |
cnindex = X509_NAME_get_index_by_NID(subj, NID_commonName, cnindex);
|
2253 | |
|
2254 | |
// Issuer cert doesn't have a CN, so just print whole thing
|
2255 | |
if (cnindex == -1)
|
2256 | |
{
|
2257 | |
char *issuer = X509_NAME_oneline(X509_get_issuer_name(x509Cert), NULL, 0);
|
2258 | |
char *color = "";
|
2259 | |
int self_signed = 0;
|
2260 | |
|
2261 | |
if ((subject != NULL) && (strcmp(subject, issuer) == 0)) {
|
2262 | |
color = COL_RED;
|
2263 | |
self_signed = 1;
|
2264 | |
}
|
2265 | |
printf("%sIssuer: %s%s", color, issuer, RESET);
|
|
2292 |
printf("Issuer: %s\n", issuer);
|
2266 | 2293 |
printf_xml(" <issuer><![CDATA[%s]]></issuer>\n", issuer);
|
2267 | |
|
2268 | |
if (self_signed) {
|
2269 | |
printf_xml(" <self-signed>true</self-signed>\n");
|
2270 | |
}
|
2271 | |
else {
|
2272 | |
printf_xml(" <self-signed>false</self-signed>\n");
|
2273 | |
}
|
2274 | |
}
|
2275 | |
else
|
2276 | |
{
|
2277 | |
e = X509_NAME_get_entry(subj, cnindex);
|
2278 | |
d = X509_NAME_ENTRY_get_data(e);
|
2279 | |
issuer = (char *) ASN1_STRING_data(d);
|
2280 | |
|
2281 | |
// If issuer is same as hostname we scanned or is *, flag as self-signed
|
2282 | |
if (
|
2283 | |
strcmp(issuer, options->host) == 0
|
2284 | |
|| strcmp(issuer, subject) == 0
|
2285 | |
|| strcmp(issuer, "*") == 0
|
2286 | |
)
|
2287 | |
{
|
2288 | |
printf("Issuer: %s%s%s\n", COL_RED, issuer, RESET);
|
2289 | |
printf_xml(" <issuer><![CDATA[%s]]></issuer>\n", issuer);
|
2290 | |
printf_xml(" <self-signed>true</self-signed>\n");
|
2291 | |
|
2292 | |
}
|
2293 | |
else
|
2294 | |
{
|
2295 | |
printf("Issuer: %s\n", issuer);
|
2296 | |
printf_xml(" <issuer><![CDATA[%s]]></issuer>\n", issuer);
|
2297 | |
printf_xml(" <self-signed>false</self-signed>\n");
|
2298 | |
}
|
|
2294 |
printf_xml(" <self-signed>false</self-signed>\n");
|
2299 | 2295 |
}
|
2300 | 2296 |
}
|
2301 | |
|
2302 | |
// Check for certificate expiration
|
2303 | |
time_t *ptime;
|
2304 | |
int timediff;
|
2305 | |
ptime = NULL;
|
2306 | |
|
2307 | |
printf("\nNot valid before: ");
|
2308 | |
timediff = X509_cmp_time(X509_get_notBefore(x509Cert), ptime);
|
2309 | |
// Certificate isn't valid yet
|
|
2297 |
}
|
|
2298 |
|
|
2299 |
// Check for certificate expiration
|
|
2300 |
time_t *ptime;
|
|
2301 |
int timediff;
|
|
2302 |
ptime = NULL;
|
|
2303 |
|
|
2304 |
printf("\nNot valid before: ");
|
|
2305 |
timediff = X509_cmp_time(X509_get_notBefore(x509Cert), ptime);
|
|
2306 |
// Certificate isn't valid yet
|
|
2307 |
if (timediff > 0)
|
|
2308 |
{
|
|
2309 |
printf("%s", COL_RED);
|
|
2310 |
}
|
|
2311 |
else
|
|
2312 |
{
|
|
2313 |
printf("%s", COL_GREEN);
|
|
2314 |
}
|
|
2315 |
ASN1_TIME_print(stdoutBIO, X509_get_notBefore(x509Cert));
|
|
2316 |
printf("%s", RESET);
|
|
2317 |
|
|
2318 |
if (options->xmlOutput) {
|
|
2319 |
printf_xml(" <not-valid-before>");
|
|
2320 |
ASN1_TIME_print(fileBIO, X509_get_notBefore(x509Cert));
|
|
2321 |
printf_xml("</not-valid-before>\n");
|
2310 | 2322 |
if (timediff > 0)
|
2311 | 2323 |
{
|
2312 | |
printf("%s", COL_RED);
|
|
2324 |
printf_xml(" <not-yet-valid>true</not-yet-valid>\n");
|
2313 | 2325 |
}
|
2314 | 2326 |
else
|
2315 | 2327 |
{
|
2316 | |
printf("%s", COL_GREEN);
|
|
2328 |
printf_xml(" <not-yet-valid>false</not-yet-valid>\n");
|
2317 | 2329 |
}
|
2318 | |
ASN1_TIME_print(stdoutBIO, X509_get_notBefore(x509Cert));
|
2319 | |
printf("%s", RESET);
|
2320 | |
|
2321 | |
if (options->xmlOutput) {
|
2322 | |
printf_xml(" <not-valid-before>");
|
2323 | |
ASN1_TIME_print(fileBIO, X509_get_notBefore(x509Cert));
|
2324 | |
printf_xml("</not-valid-before>\n");
|
2325 | |
if (timediff > 0)
|
2326 | |
{
|
2327 | |
printf_xml(" <not-yet-valid>true</not-yet-valid>\n");
|
2328 | |
}
|
2329 | |
else
|
2330 | |
{
|
2331 | |
printf_xml(" <not-yet-valid>false</not-yet-valid>\n");
|
2332 | |
}
|
2333 | |
}
|
2334 | |
|
2335 | |
printf("\nNot valid after: ");
|
2336 | |
timediff = X509_cmp_time(X509_get_notAfter(x509Cert), ptime);
|
2337 | |
// Certificate has expired
|
|
2330 |
}
|
|
2331 |
|
|
2332 |
printf("\nNot valid after: ");
|
|
2333 |
timediff = X509_cmp_time(X509_get_notAfter(x509Cert), ptime);
|
|
2334 |
// Certificate has expired
|
|
2335 |
if (timediff < 0)
|
|
2336 |
{
|
|
2337 |
printf("%s", COL_RED);
|
|
2338 |
}
|
|
2339 |
else
|
|
2340 |
{
|
|
2341 |
printf("%s", COL_GREEN);
|
|
2342 |
}
|
|
2343 |
ASN1_TIME_print(stdoutBIO, X509_get_notAfter(x509Cert));
|
|
2344 |
printf("%s", RESET);
|
|
2345 |
if (options->xmlOutput) {
|
|
2346 |
printf_xml(" <not-valid-after>");
|
|
2347 |
ASN1_TIME_print(fileBIO, X509_get_notAfter(x509Cert));
|
|
2348 |
printf_xml("</not-valid-after>\n");
|
2338 | 2349 |
if (timediff < 0)
|
2339 | 2350 |
{
|
2340 | |
printf("%s", COL_RED);
|
|
2351 |
printf_xml(" <expired>true</expired>\n");
|
2341 | 2352 |
}
|
2342 | 2353 |
else
|
2343 | 2354 |
{
|
2344 | |
printf("%s", COL_GREEN);
|
|
2355 |
printf_xml(" <expired>false</expired>\n");
|
2345 | 2356 |
}
|
2346 | |
ASN1_TIME_print(stdoutBIO, X509_get_notAfter(x509Cert));
|
2347 | |
printf("%s", RESET);
|
2348 | |
if (options->xmlOutput) {
|
2349 | |
printf_xml(" <not-valid-after>");
|
2350 | |
ASN1_TIME_print(fileBIO, X509_get_notAfter(x509Cert));
|
2351 | |
printf_xml("</not-valid-after>\n");
|
2352 | |
if (timediff < 0)
|
2353 | |
{
|
2354 | |
printf_xml(" <expired>true</expired>\n");
|
2355 | |
}
|
2356 | |
else
|
2357 | |
{
|
2358 | |
printf_xml(" <expired>false</expired>\n");
|
2359 | |
}
|
2360 | |
}
|
2361 | |
printf("\n");
|
2362 | |
|
2363 | |
// Free X509 Certificate...
|
2364 | |
X509_free(x509Cert);
|
2365 | |
// This is abusing status a bit, but means that we'll only get the cert once
|
2366 | |
status = false;
|
2367 | 2357 |
}
|
2368 | |
|
2369 | |
else {
|
2370 | |
printf(" Unable to parse certificate\n");
|
2371 | |
}
|
2372 | |
|
2373 | |
printf_xml(" </certificate>\n");
|
2374 | |
|
2375 | |
// Free BIO
|
2376 | |
BIO_free(stdoutBIO);
|
2377 | |
if (options->xmlOutput)
|
2378 | |
BIO_free(fileBIO);
|
2379 | |
|
2380 | |
// Disconnect SSL over socket
|
2381 | |
SSL_shutdown(ssl);
|
|
2358 |
printf("\n");
|
|
2359 |
|
|
2360 |
// Free X509 Certificate...
|
|
2361 |
X509_free(x509Cert);
|
|
2362 |
// This is abusing status a bit, but means that we'll only get the cert once
|
|
2363 |
status = false;
|
2382 | 2364 |
}
|
|
2365 |
|
|
2366 |
else {
|
|
2367 |
printf(" Unable to parse certificate\n");
|
|
2368 |
}
|
|
2369 |
|
|
2370 |
printf_xml(" </certificate>\n");
|
|
2371 |
|
|
2372 |
// Free BIO
|
|
2373 |
BIO_free(stdoutBIO);
|
|
2374 |
if (options->xmlOutput)
|
|
2375 |
BIO_free(fileBIO);
|
|
2376 |
|
|
2377 |
// Disconnect SSL over socket
|
|
2378 |
SSL_shutdown(ssl);
|
2383 | 2379 |
// Free SSL object
|
2384 | 2380 |
FREE_SSL(ssl);
|
2385 | 2381 |
}
|