You are viewing a plain text version of this content. The canonical link for it is here.
Posted to mod_python-commits@quetz.apache.org by gr...@apache.org on 2003/03/07 21:04:33 UTC
cvs commit: httpd-python/test/htdocs tests.py
grisha 2003/03/07 12:04:32
Modified: src requestobject.c
test httpdconf.py test.py
test/htdocs tests.py
Log:
Reproduced and fixed the bug with headers out not going out if there was
a handler registered prior to fixup and mod_dir was used. It turnes out
that ap_internal_fast_redirect replaces pointers to headers_out and other
tables inside request, so the mod_python request object created prior to
fast_redirect gets left with stale pointers. Added a bit of code to always
make sure that we are using current tables.
Submitted by: The bug discovered by and test case created by Geert Jansen
Revision Changes Path
1.44 +47 -9 httpd-python/src/requestobject.c
Index: requestobject.c
===================================================================
RCS file: /home/cvs/httpd-python/src/requestobject.c,v
retrieving revision 1.43
retrieving revision 1.44
diff -u -r1.43 -r1.44
--- requestobject.c 31 Dec 2002 15:03:36 -0000 1.43
+++ requestobject.c 7 Mar 2003 20:04:30 -0000 1.44
@@ -884,7 +884,7 @@
*/
#define OFF(x) offsetof(request_rec, x)
-
+
static struct PyMemberDef request_rec_mbrs[] = {
{"the_request", T_STRING, OFF(the_request)},
{"assbackwards", T_INT, OFF(assbackwards)},
@@ -942,8 +942,46 @@
static PyObject *getreq_recmbr(requestobject *self, void *name)
{
- return PyMember_GetOne((char*)self->request_rec,
- find_memberdef(request_rec_mbrs, name));
+ /*
+ * apparently at least ap_internal_fast_redirect blatently
+ * substitute request members, and so we always have to make
+ * sure that various apr_tables referenced haven't been
+ * replaced in between handlers and we're left with a stale.
+ */
+
+ if (strcmp(name, "headers_in") == 0) {
+ if (((tableobject*)self->headers_in)->table != self->request_rec->headers_in)
+ ((tableobject*)self->headers_in)->table = self->request_rec->headers_in;
+ Py_INCREF(self->headers_in);
+ return self->headers_in;
+ }
+ else if (strcmp(name, "headers_out") == 0) {
+ if (((tableobject*)self->headers_out)->table != self->request_rec->headers_out)
+ ((tableobject*)self->headers_out)->table = self->request_rec->headers_out;
+ Py_INCREF(self->headers_out);
+ return self->headers_out;
+ }
+ else if (strcmp(name, "err_headers_out") == 0) {
+ if (((tableobject*)self->err_headers_out)->table != self->request_rec->err_headers_out)
+ ((tableobject*)self->err_headers_out)->table = self->request_rec->err_headers_out;
+ Py_INCREF(self->err_headers_out);
+ return self->err_headers_out;
+ }
+ else if (strcmp(name, "subprocess_env") == 0) {
+ if (((tableobject*)self->subprocess_env)->table != self->request_rec->subprocess_env)
+ ((tableobject*)self->subprocess_env)->table = self->request_rec->subprocess_env;
+ Py_INCREF(self->subprocess_env);
+ return self->subprocess_env;
+ }
+ else if (strcmp(name, "notes") == 0) {
+ if (((tableobject*)self->notes)->table != self->request_rec->notes)
+ ((tableobject*)self->notes)->table = self->request_rec->notes;
+ Py_INCREF(self->notes);
+ return self->notes;
+ }
+ else
+ return PyMember_GetOne((char*)self->request_rec,
+ find_memberdef(request_rec_mbrs, name));
}
/**
@@ -1135,6 +1173,11 @@
{"finfo", (getter)getreq_rec_fi, NULL, "File information", "finfo"},
{"parsed_uri", (getter)getreq_rec_uri, NULL, "Components of URI", "parsed_uri"},
{"used_path_info", (getter)getreq_recmbr, NULL, "Flag to accept or reject path_info on current request", "used_path_info"},
+ {"headers_in", (getter)getreq_recmbr, NULL, "Incoming headers", "headers_in"},
+ {"headers_out", (getter)getreq_recmbr, NULL, "Outgoing headers", "headers_out"},
+ {"err_headers_out", (getter)getreq_recmbr, NULL, "Outgoing headers for errors", "err_headers_out"},
+ {"subprocess_env", (getter)getreq_recmbr, NULL, "Subprocess environment", "subprocess_env"},
+ {"notes", (getter)getreq_recmbr, NULL, "Notes", "notes"},
/* XXX per_dir_config */
/* XXX request_config */
/* XXX htaccess */
@@ -1147,11 +1190,6 @@
#define OFF(x) offsetof(requestobject, x)
static struct PyMemberDef request_members[] = {
- {"headers_in", T_OBJECT, OFF(headers_in), RO},
- {"headers_out", T_OBJECT, OFF(headers_out), RO},
- {"err_headers_out", T_OBJECT, OFF(err_headers_out), RO},
- {"subprocess_env", T_OBJECT, OFF(subprocess_env), RO},
- {"notes", T_OBJECT, OFF(notes), RO},
{"_content_type_set", T_INT, OFF(content_type_set), RO},
{"phase", T_OBJECT, OFF(phase), RO},
{"extension", T_STRING, OFF(extension), RO},
1.7 +9 -1 httpd-python/test/httpdconf.py
Index: httpdconf.py
===================================================================
RCS file: /home/cvs/httpd-python/test/httpdconf.py,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -r1.6 -r1.7
--- httpdconf.py 23 Jan 2003 20:20:00 -0000 1.6
+++ httpdconf.py 7 Mar 2003 20:04:31 -0000 1.7
@@ -135,6 +135,10 @@
def __init__(self, dir, *args):
ContainerTag.__init__(self, self.__class__.__name__, dir, args)
+class DirectoryIndex(Directive):
+ def __init__(self, val):
+ Directive.__init__(self, self.__class__.__name__, val)
+
class DocumentRoot(Directive):
def __init__(self, val):
Directive.__init__(self, self.__class__.__name__, val)
@@ -208,6 +212,10 @@
Directive.__init__(self, self.__class__.__name__, val)
class PythonHandler(Directive):
+ def __init__(self, val):
+ Directive.__init__(self, self.__class__.__name__, val)
+
+class PythonAccessHandler(Directive):
def __init__(self, val):
Directive.__init__(self, self.__class__.__name__, val)
1.29 +5 -3 httpd-python/test/test.py
Index: test.py
===================================================================
RCS file: /home/cvs/httpd-python/test/test.py,v
retrieving revision 1.28
retrieving revision 1.29
diff -u -r1.28 -r1.29
--- test.py 12 Feb 2003 16:10:13 -0000 1.28
+++ test.py 7 Mar 2003 20:04:31 -0000 1.29
@@ -573,8 +573,10 @@
ServerName("test_req_headers_out"),
DocumentRoot(DOCUMENT_ROOT),
Directory(DOCUMENT_ROOT,
- SetHandler("python-program"),
+ AddHandler("python-program .py"),
+ DirectoryIndex("/tests.py"),
PythonHandler("tests::req_headers_out"),
+ PythonAccessHandler("tests::req_headers_out_access"),
PythonDebug("On")))
return str(c)
@@ -583,7 +585,7 @@
print "\n * Testing req.headers_out"
conn = httplib.HTTPConnection("127.0.0.1:%s" % PORT)
- conn.putrequest("GET", "/tests.py", skip_host=1)
+ conn.putrequest("GET", "/", skip_host=1)
conn.putheader("Host", "test_req_headers_out:%s" % PORT)
conn.endheaders()
response = conn.getresponse()
1.26 +5 -1 httpd-python/test/htdocs/tests.py
Index: tests.py
===================================================================
RCS file: /home/cvs/httpd-python/test/htdocs/tests.py,v
retrieving revision 1.25
retrieving revision 1.26
diff -u -r1.25 -r1.26
--- tests.py 12 Feb 2003 16:10:13 -0000 1.25
+++ tests.py 7 Mar 2003 20:04:32 -0000 1.26
@@ -654,6 +654,10 @@
return apache.OK
+def req_headers_out_access(req):
+
+ return apache.OK
+
def srv_register_cleanup(req):
req.cleanup_data = "test ok"