Skip to content
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions UPGRADING
Original file line number Diff line number Diff line change
Expand Up @@ -264,5 +264,8 @@ PHP 8.6 UPGRADE NOTES
. Improved performance of intval('+0b...', 2) and intval('0b...', 2).
. Improved performance of str_split().

- URI:
. Reduced allocations when reading RFC3986 IPv6/IPFuture hosts and paths.

- Zip:
. Avoid string copies in ZipArchive::addFromString().
43 changes: 30 additions & 13 deletions ext/uri/uri_parser_rfc3986.c
Original file line number Diff line number Diff line change
Expand Up @@ -237,13 +237,14 @@ ZEND_ATTRIBUTE_NONNULL static zend_result php_uri_parser_rfc3986_host_read(void
if (has_text_range(&uriparser_uri->hostText)) {
if (uriparser_uri->hostData.ip6 != NULL || uriparser_uri->hostData.ipFuture.first != NULL) {
/* the textual representation of the host is always accessible in the .hostText field no matter what the host is */
smart_str host_str = {0};

smart_str_appendc(&host_str, '[');
smart_str_appendl(&host_str, uriparser_uri->hostText.first, get_text_range_length(&uriparser_uri->hostText));
smart_str_appendc(&host_str, ']');

ZVAL_NEW_STR(retval, smart_str_extract(&host_str));
const size_t host_len = get_text_range_length(&uriparser_uri->hostText);

zend_string *host_str = zend_string_concat3(
"[", 1,
uriparser_uri->hostText.first, host_len,
"]", 1
);
ZVAL_NEW_STR(retval, host_str);
Comment thread
LamentXU123 marked this conversation as resolved.
Outdated
} else {
ZVAL_STRINGL(retval, uriparser_uri->hostText.first, get_text_range_length(&uriparser_uri->hostText));
}
Expand Down Expand Up @@ -349,20 +350,36 @@ ZEND_ATTRIBUTE_NONNULL static zend_result php_uri_parser_rfc3986_path_read(void
const UriUriA *uriparser_uri = get_uri_for_reading(uri, read_mode);

if (uriparser_uri->pathHead != NULL) {
smart_str str = {0};
size_t total_len = 0;
const bool need_leading_slash = uriparser_uri->absolutePath || uriHasHostA(uriparser_uri);

if (need_leading_slash) {
total_len++;
}

for (const UriPathSegmentA *p = uriparser_uri->pathHead; p; p = p->next) {
total_len += get_text_range_length(&p->text);
if (p->next) {
total_len++;
}
}

zend_string *str = zend_string_alloc(total_len, false);
char *out = ZSTR_VAL(str);

if (uriparser_uri->absolutePath || uriHasHostA(uriparser_uri)) {
smart_str_appendc(&str, '/');
if (need_leading_slash) {
*(out++) = '/';
}

for (const UriPathSegmentA *p = uriparser_uri->pathHead; p; p = p->next) {
smart_str_appendl(&str, p->text.first, get_text_range_length(&p->text));
out = zend_mempcpy(out, p->text.first, get_text_range_length(&p->text));
if (p->next) {
smart_str_appendc(&str, '/');
*(out++) = '/';
}
}

ZVAL_NEW_STR(retval, smart_str_extract(&str));
*out = '\0';
ZVAL_NEW_STR(retval, str);
} else if (uriparser_uri->absolutePath) {
ZVAL_CHAR(retval, '/');
} else {
Expand Down
Loading