2020#include "Zend/zend_smart_str.h"
2121#include "Zend/zend_exceptions.h"
2222
23- void * uriparser_parse_uri (const zend_string * uri_str , const void * base_url , zval * errors , bool silent );
2423static void uriparser_free_uri (void * uri );
2524static void throw_invalid_uri_exception (void );
2625
@@ -370,15 +369,13 @@ PHP_MINIT_FUNCTION(uri_uriparser)
370369}
371370
372371static uriparser_uris_t * uriparser_create_uris (
373- UriUriA * uri , zend_string * uri_str ,
374- UriUriA * normalized_uri , zend_string * normalized_uri_str
372+ UriUriA * uri ,
373+ UriUriA * normalized_uri
375374) {
376375 uriparser_uris_t * uriparser_uris = emalloc (sizeof (uriparser_uris_t ));
377376
378377 uriparser_uris -> uri = uri ;
379- uriparser_uris -> uri_str = uri_str ;
380378 uriparser_uris -> normalized_uri = normalized_uri ;
381- uriparser_uris -> normalized_uri_str = normalized_uri_str ;
382379
383380 return uriparser_uris ;
384381}
@@ -392,34 +389,27 @@ void *uriparser_parse_uri_ex(const zend_string *uri_str, const uriparser_uris_t
392389{
393390 UriUriA * uriparser_uri = emalloc (sizeof (UriUriA ));
394391
395- /* uriparser keeps the originally passed in string, while lexbor may allocate a new one. */
396- zend_string * original_uri_str = zend_string_init (ZSTR_VAL (uri_str ), ZSTR_LEN (uri_str ), false);
397- if (ZSTR_LEN (original_uri_str ) == 0 ||
398- uriParseSingleUriExA (uriparser_uri , ZSTR_VAL (original_uri_str ), ZSTR_VAL (original_uri_str ) + ZSTR_LEN (original_uri_str ), NULL ) != URI_SUCCESS
392+ if (ZSTR_LEN (uri_str ) == 0 ||
393+ uriParseSingleUriExA (uriparser_uri , ZSTR_VAL (uri_str ), ZSTR_VAL (uri_str ) + ZSTR_LEN (uri_str ), NULL ) != URI_SUCCESS
399394 ) {
400395 efree (uriparser_uri );
401- zend_string_release_ex (original_uri_str , false);
402396 if (!silent ) {
403397 throw_invalid_uri_exception ();
404398 }
405399
406400 return NULL ;
407401 }
408402
403+ uriMakeOwnerA (uriparser_uri );
409404 if (uriparser_base_urls == NULL ) {
410- return uriparser_create_uris (uriparser_uri , original_uri_str , NULL , NULL );
405+ return uriparser_create_uris (uriparser_uri , NULL );
411406 }
412407
413- UriUriA * uriparser_base_url = uriparser_copy_uri (uriparser_base_urls -> uri );
414-
415408 UriUriA * absolute_uri = emalloc (sizeof (UriUriA ));
416409
417- if (uriAddBaseUriExA (absolute_uri , uriparser_uri , uriparser_base_url , URI_RESOLVE_STRICTLY ) != URI_SUCCESS ) {
418- zend_string_release_ex (original_uri_str , false);
410+ if (uriAddBaseUriExA (absolute_uri , uriparser_uri , uriparser_base_urls -> uri , URI_RESOLVE_STRICTLY ) != URI_SUCCESS ) {
419411 uriFreeUriMembersA (uriparser_uri );
420412 efree (uriparser_uri );
421- uriFreeUriMembersA (uriparser_base_url );
422- efree (uriparser_base_url );
423413 efree (absolute_uri );
424414
425415 if (!silent ) {
@@ -429,15 +419,11 @@ void *uriparser_parse_uri_ex(const zend_string *uri_str, const uriparser_uris_t
429419 return NULL ;
430420 }
431421
432- /* TODO fix freeing: if the following code runs, then we'll have use-after-free-s because uriparser doesn't
433- copy the input. If we don't run the following code, then we'll have memory leaks...
434- uriFreeUriMembersA(uriparser_base_url);
435- efree(uriparser_base_url);
422+ uriMakeOwnerA (absolute_uri );
436423 uriFreeUriMembersA (uriparser_uri );
437424 efree (uriparser_uri );
438- */
439425
440- return uriparser_create_uris (absolute_uri , original_uri_str , NULL , NULL );
426+ return uriparser_create_uris (absolute_uri , NULL );
441427}
442428
443429void * uriparser_parse_uri (const zend_string * uri_str , const void * base_url , zval * errors , bool silent )
@@ -451,9 +437,7 @@ static void *uriparser_clone_uri(void *uri)
451437
452438 return uriparser_create_uris (
453439 uriparser_copy_uri (uriparser_uris -> uri ),
454- zend_string_copy (uriparser_uris -> uri_str ),
455- uriparser_uris -> normalized_uri != NULL ? uriparser_copy_uri (uriparser_uris -> normalized_uri ) : NULL ,
456- uriparser_uris -> normalized_uri_str != NULL ? zend_string_copy (uriparser_uris -> normalized_uri_str ) : NULL
440+ uriparser_uris -> normalized_uri != NULL ? uriparser_copy_uri (uriparser_uris -> normalized_uri ) : NULL
457441 );
458442}
459443
@@ -500,22 +484,13 @@ static void uriparser_free_uri(void *uri)
500484 uriparser_uris_t * uriparser_uris = (uriparser_uris_t * ) uri ;
501485
502486 if (uriparser_uris -> uri != NULL ) {
503- if (uriparser_uris -> uri_str != NULL ) { // TODO can this double free? should we check uriparser_uris->uri->owner?
504- zend_string_release (uriparser_uris -> uri_str );
505- uriparser_uris -> uri_str = NULL ;
506- }
507-
508487 uriFreeUriMembersA (uriparser_uris -> uri );
509488 efree (uriparser_uris -> uri );
510489 uriparser_uris -> uri = NULL ;
511490 }
512491
513492 if (uriparser_uris -> normalized_uri != NULL ) {
514493 ZEND_ASSERT (uriparser_uris -> normalized_uri -> owner );
515- if (uriparser_uris -> normalized_uri_str != NULL ) {
516- zend_string_release (uriparser_uris -> normalized_uri_str );
517- uriparser_uris -> normalized_uri_str = NULL ;
518- }
519494
520495 uriFreeUriMembersA (uriparser_uris -> normalized_uri );
521496 efree (uriparser_uris -> normalized_uri );
0 commit comments