stas 2003/03/09 00:57:55
Modified: . Changes lib/Apache compat.pm t/response/TestAPI uri.pm xs/APR/URI APR__URI.h Added: t/response/TestCompat apache_uri.pm Log: - fixes for apr_uri_unparse, which has the segfault resolved in apr-0.9.2, but is not using the default 'http' scheme if such is not provided. So we have to do special overriding in Apache::compat to keep the mp1-like behavior. - adjust/add tests Revision Changes Path 1.147 +3 -1 modperl-2.0/Changes Index: Changes =================================================================== RCS file: /home/cvs/modperl-2.0/Changes,v retrieving revision 1.146 retrieving revision 1.147 diff -u -r1.146 -r1.147 --- Changes 8 Mar 2003 09:49:26 -0000 1.146 +++ Changes 9 Mar 2003 08:57:55 -0000 1.147 @@ -62,7 +62,9 @@ missing. [Stas] fix a bug for apr < 0.9.3, where it segfaults in apr_uri_unparse, if -hostname is set, but not the scheme. [Stas] +hostname is set, but not the scheme. In case the hostname is defined +but scheme is not Apache::compat will default to the 'http' scheme, +whereas APR::URI::unparse provides no default [Stas] move $r->send_http_header implementation to Apache::compat. This allows the 1.0 code to run unmodified if $r->send_http_header is 1.84 +20 -3 modperl-2.0/lib/Apache/compat.pm Index: compat.pm =================================================================== RCS file: /home/cvs/modperl-2.0/lib/Apache/compat.pm,v retrieving revision 1.83 retrieving revision 1.84 diff -u -r1.83 -r1.84 --- compat.pm 8 Mar 2003 09:15:16 -0000 1.83 +++ compat.pm 9 Mar 2003 08:57:55 -0000 1.84 @@ -2,6 +2,7 @@ use strict; use warnings FATAL => 'all'; +no warnings 'redefine'; #1.xx compat layer #some of this will stay as-is @@ -418,17 +419,17 @@ # cannot forward @_ to open() because of its prototype if (@_ > 1) { my ($mode, $file) = @_; - open $self, $mode, $file; + CORE::open $self, $mode, $file; } else { my $file = shift; - open $self, $file; + CORE::open $self, $file; } } sub close { my($self) = shift; - close $self; + CORE::close $self; } my $TMPNAM = 'aaaaaa'; @@ -541,6 +542,22 @@ $uri ||= $r->construct_url; APR::URI->parse($r->pool, $uri); +} + +{ + my $sub = *APR::URI::unparse{CODE}; + *APR::URI::unparse = sub { + my($uri, $flags) = @_; + + if (defined $uri->hostname && !defined $uri->scheme) { + # we do this only for back compat, the new APR::URI is + # protocol-agnostic and doesn't fallback to 'http' when the + # scheme is not provided + $uri->scheme('http'); + } + + $sub->(@_); + }; } package Apache::Table; 1.10 +23 -3 modperl-2.0/t/response/TestAPI/uri.pm Index: uri.pm =================================================================== RCS file: /home/cvs/modperl-2.0/t/response/TestAPI/uri.pm,v retrieving revision 1.9 retrieving revision 1.10 diff -u -r1.9 -r1.10 --- uri.pm 20 Feb 2003 01:28:24 -0000 1.9 +++ uri.pm 9 Mar 2003 08:57:55 -0000 1.10 @@ -18,6 +18,14 @@ sub handler { my $r = shift; + # since Apache::compat redefines APR::URI::unparse and the test for + # backcompat Apache::URI forces redefinition of APR::URI::unparse + # (to get the right behavior during the test), + # we need to force reload of APR::URI + delete $INC{"APR/URI.pm"}; + no warnings 'redefine'; + require APR::URI; + plan $r, tests => 15; $r->args('query'); @@ -52,14 +60,26 @@ ok $parsed->path eq $path; { - # test the segfault in apr < 0.9.3 (fixed on mod_perl side) + # test the segfault in apr < 0.9.2 (fixed on mod_perl side) # passing only the /path my $parsed = APR::URI->parse($r->pool, $r->uri); # set hostname, but not the scheme $parsed->hostname($r->get_server_name); $parsed->port($r->get_server_port); - #$parsed->scheme('http'); - ok t_cmp($r->construct_url, $parsed->unparse); + #$parsed->scheme('http'); + my $expected = $r->construct_url; + my $received = $parsed->unparse; + t_debug("the real received is: $received"); + # apr < 0.9.2-dev + fix in mpxs_apr_uri_unparse will return + # '://localhost.localdomain:8529/TestAPI::uri' + # apr >= 0.9.2 with internal fix will return + # '//localhost.localdomain:8529/TestAPI::uri' + # so in order to test pre-0.9.2 and post-0.9.2-dev we massage it + $expected =~ s|^http:||; + $received =~ s|^:||; + ok t_cmp($expected, $received, + "the bogus url is expected when 'hostname' is set " . + "but not 'scheme'"); } my $newr = Apache::RequestRec->new($r->connection, $r->pool); 1.1 modperl-2.0/t/response/TestCompat/apache_uri.pm Index: apache_uri.pm =================================================================== package TestCompat::apache_uri; # Apache::Util compat layer tests # these tests are all run and validated on the server side. use strict; use warnings FATAL => 'all'; use Apache::TestUtil; use Apache::Test; use Apache::compat (); use Apache::Constants qw(OK); sub handler { my $r = shift; plan $r, tests => 1; # XXX: need to test ->parse # { # my @methods = qw(scheme hostinfo user password hostname path rpath # query fragment port unparse); # my $test_uri = "http://foo:[EMAIL PROTECTED]:80/docs/index.html"; # # for my $uri ($r->parsed_uri, Apache::URI->parse($r, $test_uri)) { # t_debug("URI=" . $uri->unparse); # no strict 'refs'; # for my $meth (@methods) { # my $val = $uri->$meth(); # t_debug("$meth: $val"); # ok $val || 1; # } # } # } { # since Apache::compat redefines APR::URI::unparse and the test for # real APR::URI forces reload of APR::URI (to get the right behavior), # we need to force reload of Apache::compat delete $INC{"Apache/compat.pm"}; require Apache::compat; # test the segfault in apr < 0.9.2 (fixed on mod_perl side) # passing only the /path my $parsed = APR::URI->parse($r->pool, $r->uri); # set hostname, but not the scheme $parsed->hostname($r->get_server_name); $parsed->port($r->get_server_port); #$parsed->scheme('http'); # compat defaults to 'http' like apache-1.3 did ok t_cmp($r->construct_url, $parsed->unparse); } OK; } 1; 1.6 +8 -4 modperl-2.0/xs/APR/URI/APR__URI.h Index: APR__URI.h =================================================================== RCS file: /home/cvs/modperl-2.0/xs/APR/URI/APR__URI.h,v retrieving revision 1.5 retrieving revision 1.6 diff -u -r1.5 -r1.6 --- APR__URI.h 20 Feb 2003 01:28:24 -0000 1.5 +++ APR__URI.h 9 Mar 2003 08:57:55 -0000 1.6 @@ -4,11 +4,15 @@ unsigned flags) { - /* XXX: check that my patch was actually applied in apr v9.3 */ -#if APR_MINOR_VERSION == 9 && APR_PATCH_VERSION < 3 - /* apr < 0.9.3 segfaults if hostname is set, but scheme is not */ + /* apr =< 0.9.2-dev segfaults if hostname is set, but scheme is not. + * apr >= 0.9.2 simply uses "", which will force the user to set scheme + * since apr_uri_unparse is protocol-agnostic, it doesn't use + * 'http' as the default fallback anymore. so we use the same solution + */ +#if APR_MAJOR_VERSION == 0 && APR_MINOR_VERSION == 9 && \ + (APR_PATCH_VERSION < 2 || APR_PATCH_VERSION == 2 && defined APR_IS_DEV_VERSION) if (uptr->hostname && !uptr->scheme) { - uptr->scheme = "http"; + uptr->scheme = ""; } #endif