On 06 Oct 2015, at 12:36 PM, Yann Ylavic <ylavic....@gmail.com> wrote:

>> Although the brigade is empty, don't we need to prevent the brigade being 
>> used by multiple threads in parallel?
>> Using one per connection prevents this.
> 
> Hmm, the filters are also allocated per connection/request (on
> c/r->pool), and shouldn't be called concurrently right?

Yes.

> BTW, I wonder if we can "reinstate" the filters in arbitrary order
> like in the above loop (the order seems to depend on the calls to
> ap_filter_setaside_brigade() and internal apr_hash_t ordering).
> Don't we need to start from r->ouput_filters down to the last filter
> and call ap_pass_brigade(f, c->empty) if f is in the hashtable?

No - we don’t “reinstate” filters in any way, we just kick them. We kick each 
eligible filter exactly once on each pass, and the order doesn’t matter. Every 
filter with data in it gets a kick to ensure no filter is starved, all filters 
without data are silently ignored.

When a kick arrives and the filter has something to write, the normal filter 
stack write order is preserved by ap_pass_brigade() and everything happens in 
the right order naturally without us having to do anything special.

Typically only two filters at a time - the bottleneck and the network filter - 
will have data in it, all other filters will be empty. If mod_cache is present, 
then three filters are likely to have data in it (mod_cache, the bottleneck 
filter and the network filter), and three filters will get kicked.

When I was investigating this I was originally looking at a skiplist to keep 
the ordering, but once I analysed it it turned out to be unnecessary.

Regards,
Graham
—

Reply via email to