[ Index ] |
PHP Cross Reference of WordPress |
[Summary view] [Print] [Text view]
1 <?php 2 /** 3 * SSL utilities for Requests 4 * 5 * @package Requests 6 * @subpackage Utilities 7 */ 8 9 /** 10 * SSL utilities for Requests 11 * 12 * Collection of utilities for working with and verifying SSL certificates. 13 * 14 * @package Requests 15 * @subpackage Utilities 16 */ 17 class Requests_SSL { 18 /** 19 * Verify the certificate against common name and subject alternative names 20 * 21 * Unfortunately, PHP doesn't check the certificate against the alternative 22 * names, leading things like 'https://www.github.com/' to be invalid. 23 * 24 * @see https://tools.ietf.org/html/rfc2818#section-3.1 RFC2818, Section 3.1 25 * 26 * @throws Requests_Exception On not obtaining a match for the host (`fsockopen.ssl.no_match`) 27 * @param string $host Host name to verify against 28 * @param array $cert Certificate data from openssl_x509_parse() 29 * @return bool 30 */ 31 public static function verify_certificate($host, $cert) { 32 $has_dns_alt = false; 33 34 // Check the subjectAltName 35 if (!empty($cert['extensions']) && !empty($cert['extensions']['subjectAltName'])) { 36 $altnames = explode(',', $cert['extensions']['subjectAltName']); 37 foreach ($altnames as $altname) { 38 $altname = trim($altname); 39 if (strpos($altname, 'DNS:') !== 0) { 40 continue; 41 } 42 43 $has_dns_alt = true; 44 45 // Strip the 'DNS:' prefix and trim whitespace 46 $altname = trim(substr($altname, 4)); 47 48 // Check for a match 49 if (self::match_domain($host, $altname) === true) { 50 return true; 51 } 52 } 53 } 54 55 // Fall back to checking the common name if we didn't get any dNSName 56 // alt names, as per RFC2818 57 if (!$has_dns_alt && !empty($cert['subject']['CN'])) { 58 // Check for a match 59 if (self::match_domain($host, $cert['subject']['CN']) === true) { 60 return true; 61 } 62 } 63 64 return false; 65 } 66 67 /** 68 * Verify that a reference name is valid 69 * 70 * Verifies a dNSName for HTTPS usage, (almost) as per Firefox's rules: 71 * - Wildcards can only occur in a name with more than 3 components 72 * - Wildcards can only occur as the last character in the first 73 * component 74 * - Wildcards may be preceded by additional characters 75 * 76 * We modify these rules to be a bit stricter and only allow the wildcard 77 * character to be the full first component; that is, with the exclusion of 78 * the third rule. 79 * 80 * @param string $reference Reference dNSName 81 * @return boolean Is the name valid? 82 */ 83 public static function verify_reference_name($reference) { 84 $parts = explode('.', $reference); 85 86 // Check the first part of the name 87 $first = array_shift($parts); 88 89 if (strpos($first, '*') !== false) { 90 // Check that the wildcard is the full part 91 if ($first !== '*') { 92 return false; 93 } 94 95 // Check that we have at least 3 components (including first) 96 if (count($parts) < 2) { 97 return false; 98 } 99 } 100 101 // Check the remaining parts 102 foreach ($parts as $part) { 103 if (strpos($part, '*') !== false) { 104 return false; 105 } 106 } 107 108 // Nothing found, verified! 109 return true; 110 } 111 112 /** 113 * Match a hostname against a dNSName reference 114 * 115 * @param string $host Requested host 116 * @param string $reference dNSName to match against 117 * @return boolean Does the domain match? 118 */ 119 public static function match_domain($host, $reference) { 120 // Check if the reference is blocklisted first 121 if (self::verify_reference_name($reference) !== true) { 122 return false; 123 } 124 125 // Check for a direct match 126 if ($host === $reference) { 127 return true; 128 } 129 130 // Calculate the valid wildcard match if the host is not an IP address 131 // Also validates that the host has 3 parts or more, as per Firefox's 132 // ruleset. 133 if (ip2long($host) === false) { 134 $parts = explode('.', $host); 135 $parts[0] = '*'; 136 $wildcard = implode('.', $parts); 137 if ($wildcard === $reference) { 138 return true; 139 } 140 } 141 142 return false; 143 } 144 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
Generated: Thu Dec 15 01:00:02 2022 | Cross-referenced by PHPXref 0.7.1 |