Hi, 

This is a bug similar to PR 33112 which was fixed in 2.2.6.

Query strings are not being passed along when mod_negotiation
combines  multiviews with typemap processing.

The guilty party is the call to 

   ap_internal_fast_redirect(sub_req, r)

in mod_negotiation.c:handle_multi() which discards the 
previously parsed args and path_info. That info is 
not regenerated again. I'm including a very naive patch 
against 2.2.6 that fixes this.  I'm sure there is a 
better way to fix it, but need more of your guidance 
to achieve it in an optimal way.

Here's a test scenario to show this bug. Please adjust accordingly
to your server setup. I assume the use of php
for printing out the query parameters; you could use
perl or a shell script too):

1. In a directory, put the three files that I've attached:
   test.html, test.php, test.var

2. query the server for test.php?q=3  
        
           http://localhost/test.php?q=3

    ==> you'll see that the query parameters are correctly
        passed to the script.

3. query the server for test?q=3

           http://localhost/test?q=3

    ==> in this case, the query parameters have been discarded
        by mod_negotiation's call to 
        ap_internal_fast_redirect inside handle_multi().

You'll see that my naive solution is to make a backup copy of
args and path_info, if they existed, before the call to 
ap_internal_fast_redirect(), and then restoring them. This
effectively solves the bug. I don't know if there's a better
way to do this.

Thanks,

-jose
Title: type map test

you shouldn't see this html file

URI: test

URI: test.php
Content-type: text/html;qs=1.0

URI: test.html
Content-type: text/html;qs=0.01

Attachment: test.php
Description: application/httpd-php

--- mod_negotiation.c.orig	2007-09-25 15:47:37.000000000 +0200
+++ mod_negotiation.c	2007-09-25 15:47:45.000000000 +0200
@@ -3132,7 +3132,28 @@
     }
 
     /* now do a "fast redirect" ... promotes the sub_req into the main req */
-    ap_internal_fast_redirect(sub_req, r);
+    {
+      /* save the previous parsed args and path_info */
+      char *args;
+      char *path_info;
+      
+      if (r->args) {
+	args = apr_pstrdup(r->pool, r->args);
+      } else {
+	args = NULL;
+      }
+
+      if (r->path_info) {
+	r->path_info = apr_pstrdup(r->pool, r->path_info);
+      } else {
+	path_info = NULL;
+      }
+      ap_internal_fast_redirect(sub_req, r);
+
+      /* restore the parsed args and path info */
+      r->args = args;
+      r->path_info = path_info;
+    }
 
     /* give no advise for time on this subrequest.  Perhaps we
      * should tally the last mtime amoung all variants, and date

Reply via email to