This fixes most of the header bug that was committed last night. The server

is seg faulting on pipelined requests currently, but I want to get people
back to a running server.


git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@93686 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Ryan Bloom
2002-03-03 22:04:03 +00:00
parent d181d7e4f5
commit 596d79f14b
3 changed files with 88 additions and 113 deletions

View File

@ -776,6 +776,10 @@ request_rec *ap_read_request(conn_rec *conn)
r->request_config = ap_create_request_config(r->pool);
/* Must be set before we run create request hook */
conn->output_filters->prev = NULL;
conn->input_filters->prev = NULL;
r->proto_output_filters = conn->output_filters;
r->output_filters = r->proto_output_filters;
r->proto_input_filters = conn->input_filters;

View File

@ -1492,7 +1492,12 @@ static request_rec *make_sub_request(const request_rec *r,
/* start with the same set of output filters */
if (next_filter) {
/* no input filters for a subrequest */
/* while there are no input filters for a subrequest, we will
* try to insert some, so if we don't have valid data, the code
* will seg fault.
*/
rnew->input_filters = r->input_filters;
rnew->proto_input_filters = r->proto_input_filters;
rnew->output_filters = next_filter;
ap_add_output_filter_handle(ap_subreq_core_filter_handle,
NULL, rnew, rnew->connection);

View File

@ -291,108 +291,6 @@ AP_DECLARE(ap_filter_rec_t *) ap_register_output_filter(const char *name,
return register_filter(name, f, ftype, &registered_output_filters);
}
static ap_filter_t *add_any_filter(const char *name, void *ctx,
request_rec *r, conn_rec *c,
const filter_trie_node *reg_filter_set,
ap_filter_t **r_filters,
ap_filter_t **p_filters,
ap_filter_t **c_filters)
{
if (reg_filter_set) {
const char *n;
const filter_trie_node *node;
node = reg_filter_set;
for (n = name; *n; n++) {
int start, end;
start = 0;
end = node->nchildren - 1;
while (end >= start) {
int middle = (end + start) / 2;
char ch = node->children[middle].c;
if (*n == ch) {
node = node->children[middle].child;
break;
}
else if (*n < ch) {
end = middle - 1;
}
else {
start = middle + 1;
}
}
if (end < start) {
node = NULL;
break;
}
}
if (node && node->frec) {
apr_pool_t* p = r ? r->pool : c->pool;
ap_filter_t *f = apr_palloc(p, sizeof(*f));
ap_filter_t **outf;
if (node->frec->ftype < AP_FTYPE_HTTP_HEADER) {
if (r) {
outf = r_filters;
}
else {
ap_log_error(APLOG_MARK, APLOG_ERR|APLOG_NOERRNO, 0, NULL,
"a content filter was added without a request: %s", name);
return NULL;
}
}
else if (node->frec->ftype < AP_FTYPE_CONNECTION) {
if (r) {
outf = p_filters;
}
else {
ap_log_error(APLOG_MARK, APLOG_ERR|APLOG_NOERRNO, 0, NULL,
"a protocol filter was added without a request: %s", name);
return NULL;
}
}
else {
outf = c_filters;
}
f->frec = node->frec;
f->ctx = ctx;
f->r = r;
f->c = c;
if (INSERT_BEFORE(f, *outf)) {
f->next = *outf;
if ((*outf) && (*outf)->prev) {
f->prev = (*outf)->prev;
(*outf)->prev->next = f;
(*outf)->prev = f;
}
else {
f->prev = NULL;
}
*outf = f;
}
else {
ap_filter_t *fscan = *outf;
while (!INSERT_BEFORE(f, fscan->next))
fscan = fscan->next;
f->next = fscan->next;
f->prev = fscan;
fscan->next->prev = f;
fscan->next = f;
}
return f;
}
}
ap_log_error(APLOG_MARK, APLOG_ERR|APLOG_NOERRNO, 0, NULL,
"an unknown filter was not added: %s", name);
return NULL;
}
static ap_filter_t *add_any_filter_handle(ap_filter_rec_t *frec, void *ctx,
request_rec *r, conn_rec *c,
ap_filter_t **r_filters,
@ -431,16 +329,33 @@ static ap_filter_t *add_any_filter_handle(ap_filter_rec_t *frec, void *ctx,
f->ctx = ctx;
f->r = r;
f->c = c;
f->next = f->prev = NULL;
if (INSERT_BEFORE(f, *outf)) {
f->next = *outf;
if ((*outf) && (*outf)->prev) {
f->prev = (*outf)->prev;
(*outf)->prev->next = f;
(*outf)->prev = f;
}
else {
f->prev = NULL;
if (*outf) {
ap_filter_t *first = NULL;
if (r) {
/* If we are adding our first non-connection filter,
* Then don't try to find the right location, it is
* automatically first.
*/
if (*r_filters != *c_filters) {
first = *r_filters;
while (first && first->next && (first->next != (*outf))) {
first = first->next;
}
}
}
if (first && first != (*outf)) {
first->next = f;
f->prev = first;
}
if (*outf && ((*outf)->prev == first)) {
(*outf)->prev = f;
}
}
*outf = f;
}
@ -450,14 +365,63 @@ static ap_filter_t *add_any_filter_handle(ap_filter_rec_t *frec, void *ctx,
fscan = fscan->next;
f->next = fscan->next;
f->prev = fscan;
fscan->next->prev = f;
fscan->next = f;
if (fscan->next->prev == fscan) {
f->prev = fscan;
fscan->next->prev = f;
fscan->next = f;
}
}
return f;
}
static ap_filter_t *add_any_filter(const char *name, void *ctx,
request_rec *r, conn_rec *c,
const filter_trie_node *reg_filter_set,
ap_filter_t **r_filters,
ap_filter_t **p_filters,
ap_filter_t **c_filters)
{
if (reg_filter_set) {
const char *n;
const filter_trie_node *node;
node = reg_filter_set;
for (n = name; *n; n++) {
int start, end;
start = 0;
end = node->nchildren - 1;
while (end >= start) {
int middle = (end + start) / 2;
char ch = node->children[middle].c;
if (*n == ch) {
node = node->children[middle].child;
break;
}
else if (*n < ch) {
end = middle - 1;
}
else {
start = middle + 1;
}
}
if (end < start) {
node = NULL;
break;
}
}
if (node && node->frec) {
add_any_filter_handle(node->frec, ctx, r, c, r_filters, p_filters,
c_filters);
}
}
ap_log_error(APLOG_MARK, APLOG_ERR|APLOG_NOERRNO, 0, NULL,
"an unknown filter was not added: %s", name);
return NULL;
}
AP_DECLARE(ap_filter_t *) ap_add_input_filter(const char *name, void *ctx,
request_rec *r, conn_rec *c)
{
@ -502,6 +466,7 @@ static void remove_any_filter(ap_filter_t *f, ap_filter_t **r_filt,
if (*curr == f) {
*curr = (*curr)->next;
(*curr)->prev = NULL;
return;
}
@ -512,6 +477,7 @@ static void remove_any_filter(ap_filter_t *f, ap_filter_t **r_filt,
}
fscan->next = f->next;
f->next->prev = fscan;
}
AP_DECLARE(void) ap_remove_input_filter(ap_filter_t *f)