Skip to content

Commit 444c1df

Browse files
LamentXU123thesamesam
authored andcommitted
ext/openssl: Fix build with OpenSSL 4.1 (#24686)
OpenSSL 4.1 deprecates ASN1_STRING_set() and ASN1_STRING_length(). use ASN1_STRING_set1_data() and ASN1_STRING_get_length() instead as recommended in official doc https://docs.openssl.org/4.1/man7/ossl-guide-migration/#asn1_string-values-have-never-been-nul-byte-terminated (cherry picked from commit 3678f39)
1 parent 99a8140 commit 444c1df

3 files changed

Lines changed: 25 additions & 17 deletions

File tree

‎ext/openssl/openssl.c‎

Lines changed: 16 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -703,7 +703,7 @@ static void php_openssl_add_assoc_name_entry(zval * val, char * key, const X509_
703703
} else {
704704
/* ASN1_STRING_get0_data(3): Since this is an internal pointer it should not be freed or modified in any way */
705705
to_add = ASN1_STRING_get0_data(str);
706-
to_add_len = ASN1_STRING_length(str);
706+
to_add_len = ASN1_STRING_get_length(str);
707707
}
708708

709709
if (to_add_len != -1) {
@@ -739,7 +739,7 @@ static void php_openssl_add_assoc_name_entry(zval * val, char * key, const X509_
739739

740740
static void php_openssl_add_assoc_asn1_string(zval * val, char * key, const ASN1_STRING * str) /* {{{ */
741741
{
742-
add_assoc_stringl(val, key, (const char *)ASN1_STRING_get0_data(str), ASN1_STRING_length(str));
742+
add_assoc_stringl(val, key, (const char *)ASN1_STRING_get0_data(str), ASN1_STRING_get_length(str));
743743
}
744744
/* }}} */
745745

@@ -756,6 +756,7 @@ static time_t php_openssl_asn1_time_to_time_t(ASN1_UTCTIME * timestr) /* {{{ */
756756
struct tm thetime;
757757
char * strbuf;
758758
char * thestr;
759+
const char *timestr_data;
759760
long gmadjust = 0;
760761
size_t timestr_len;
761762

@@ -764,24 +765,25 @@ static time_t php_openssl_asn1_time_to_time_t(ASN1_UTCTIME * timestr) /* {{{ */
764765
return (time_t)-1;
765766
}
766767

767-
timestr_len = (size_t)ASN1_STRING_length(timestr);
768+
timestr_len = ASN1_STRING_get_length(timestr);
769+
timestr_data = timestr_len ? (const char *)ASN1_STRING_get0_data(timestr) : "";
768770

769-
if (timestr_len != strlen((const char *)ASN1_STRING_get0_data(timestr))) {
771+
if (memchr(timestr_data, '\0', timestr_len) != NULL) {
770772
php_error_docref(NULL, E_WARNING, "Illegal length in timestamp");
771773
return (time_t)-1;
772774
}
773775

774776
if (timestr_len < 13) {
775-
php_error_docref(NULL, E_WARNING, "Unable to parse time string %s correctly", ASN1_STRING_get0_data(timestr));
777+
php_error_docref(NULL, E_WARNING, "Unable to parse time string %.*s correctly", (int)timestr_len, timestr_data);
776778
return (time_t)-1;
777779
}
778780

779781
if (ASN1_STRING_type(timestr) == V_ASN1_GENERALIZEDTIME && timestr_len < 15) {
780-
php_error_docref(NULL, E_WARNING, "Unable to parse time string %s correctly", ASN1_STRING_get0_data(timestr));
782+
php_error_docref(NULL, E_WARNING, "Unable to parse time string %.*s correctly", (int)timestr_len, timestr_data);
781783
return (time_t)-1;
782784
}
783785

784-
strbuf = estrdup((const char *)ASN1_STRING_get0_data(timestr));
786+
strbuf = estrndup(timestr_data, timestr_len);
785787

786788
memset(&thetime, 0, sizeof(thetime));
787789

@@ -1632,7 +1634,7 @@ PHP_FUNCTION(openssl_spki_new)
16321634
}
16331635

16341636
if (challenge) {
1635-
if (!ASN1_STRING_set(spki->spkac->challenge, challenge, (int)challenge_len)) {
1637+
if (!ASN1_STRING_set1_data(spki->spkac->challenge, (const unsigned char *) challenge, challenge_len)) {
16361638
php_openssl_store_errors();
16371639
php_error_docref(NULL, E_WARNING, "Unable to set challenge data");
16381640
goto cleanup;
@@ -1824,7 +1826,8 @@ PHP_FUNCTION(openssl_spki_export_challenge)
18241826
goto cleanup;
18251827
}
18261828

1827-
RETVAL_STRING((const char *)ASN1_STRING_get0_data(spki->spkac->challenge));
1829+
RETVAL_STRINGL_FAST((const char *)ASN1_STRING_get0_data(spki->spkac->challenge),
1830+
ASN1_STRING_get_length(spki->spkac->challenge));
18281831
goto cleanup;
18291832

18301833
cleanup:
@@ -2041,7 +2044,7 @@ static int openssl_x509v3_subjectAltName(BIO *bio, PHP_OPENSSL_X509_EXTENSION *e
20412044

20422045
extension_data = X509_EXTENSION_get_data(extension);
20432046
p = ASN1_STRING_get0_data(extension_data);
2044-
length = ASN1_STRING_length(extension_data);
2047+
length = ASN1_STRING_get_length(extension_data);
20452048
if (method->it) {
20462049
names = (GENERAL_NAMES*) (ASN1_item_d2i(NULL, &p, length,
20472050
ASN1_ITEM_ptr(method->it)));
@@ -2063,19 +2066,19 @@ static int openssl_x509v3_subjectAltName(BIO *bio, PHP_OPENSSL_X509_EXTENSION *e
20632066
BIO_puts(bio, "email:");
20642067
as = name->d.rfc822Name;
20652068
BIO_write(bio, ASN1_STRING_get0_data(as),
2066-
ASN1_STRING_length(as));
2069+
ASN1_STRING_get_length(as));
20672070
break;
20682071
case GEN_DNS:
20692072
BIO_puts(bio, "DNS:");
20702073
as = name->d.dNSName;
20712074
BIO_write(bio, ASN1_STRING_get0_data(as),
2072-
ASN1_STRING_length(as));
2075+
ASN1_STRING_get_length(as));
20732076
break;
20742077
case GEN_URI:
20752078
BIO_puts(bio, "URI:");
20762079
as = name->d.uniformResourceIdentifier;
20772080
BIO_write(bio, ASN1_STRING_get0_data(as),
2078-
ASN1_STRING_length(as));
2081+
ASN1_STRING_get_length(as));
20792082
break;
20802083
default:
20812084
/* use builtin print for GEN_OTHERNAME, GEN_X400,

‎ext/openssl/php_openssl.h‎

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,11 @@ extern zend_module_entry openssl_module_entry;
4646
#endif
4747
#endif
4848

49+
#if OPENSSL_VERSION_NUMBER < 0x40100000L
50+
#define ASN1_STRING_set1_data(str, data, len) ASN1_STRING_set((str), (data), (int) (len))
51+
#define ASN1_STRING_get_length(str) ((size_t) ASN1_STRING_length(str))
52+
#endif
53+
4954
#if defined(OPENSSL_VERSION_MAJOR) && OPENSSL_VERSION_MAJOR >= 4
5055
typedef const X509_EXTENSION PHP_OPENSSL_X509_EXTENSION;
5156
#else

‎ext/openssl/xp_ssl.c‎

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -480,7 +480,7 @@ static bool php_openssl_matches_san_list(
480480
/* TODO: warn ? */
481481
continue;
482482
}
483-
if ((size_t)ASN1_STRING_length(san->d.dNSName) != strlen((const char*)cert_name)) {
483+
if (ASN1_STRING_get_length(san->d.dNSName) != strlen((const char*)cert_name)) {
484484
OPENSSL_free(cert_name);
485485
/* prevent null-byte poisoning*/
486486
continue;
@@ -500,7 +500,7 @@ static bool php_openssl_matches_san_list(
500500
}
501501
OPENSSL_free(cert_name);
502502
} else if (san->type == GEN_IPADD) {
503-
if (ASN1_STRING_length(san->d.iPAddress) == 4) {
503+
if (ASN1_STRING_get_length(san->d.iPAddress) == 4) {
504504
snprintf(ipbuffer, sizeof(ipbuffer), "%d.%d.%d.%d",
505505
ASN1_STRING_get0_data(san->d.iPAddress)[0],
506506
ASN1_STRING_get0_data(san->d.iPAddress)[1],
@@ -514,7 +514,7 @@ static bool php_openssl_matches_san_list(
514514
}
515515
}
516516
#ifdef HAVE_IPV6_SAN
517-
else if (ASN1_STRING_length(san->d.ip) == 16 && subject_name_is_ipv6) {
517+
else if (ASN1_STRING_get_length(san->d.ip) == 16 && subject_name_is_ipv6) {
518518
ipbuffer[0] = 0;
519519
EXPAND_IPV6_ADDRESS(ipbuffer, ASN1_STRING_get0_data(san->d.iPAddress));
520520
if (strcasecmp((const char*)subject_name_ipv6_expanded, (const char*)ipbuffer) == 0) {
@@ -570,7 +570,7 @@ static bool php_openssl_matches_common_name(X509 *peer, const char *subject_name
570570
}
571571

572572
name_asn1 = X509_NAME_ENTRY_get_data(name_entry);
573-
cert_name_len = ASN1_STRING_length(name_asn1);
573+
cert_name_len = ASN1_STRING_get_length(name_asn1);
574574
cert_name = (unsigned char *) OPENSSL_strndup((const char *) ASN1_STRING_get0_data(name_asn1), cert_name_len);
575575
if (cert_name == NULL) {
576576
php_error_docref(NULL, E_WARNING, "Unable to locate peer certificate CN");

0 commit comments

Comments
 (0)